aboutsummaryrefslogtreecommitdiffstats
path: root/history-search
diff options
context:
space:
mode:
authorTom Feist <shabble@cowu.be>2010-07-24 16:35:43 +0000
committerTom Feist <shabble@cowu.be>2010-07-24 16:35:43 +0000
commit501309887a7499b91c2b9fa8f76180c2738d7990 (patch)
tree5bc5f26da277c8b4c7d66c5863ba365723dc6c53 /history-search
parentmisc stuffs (diff)
downloadirssi-scripts-501309887a7499b91c2b9fa8f76180c2738d7990.tar.gz
irssi-scripts-501309887a7499b91c2b9fa8f76180c2738d7990.zip
something confusing going on here, have I got nested repos?
Diffstat (limited to 'history-search')
-rw-r--r--history-search/complete_test.pl27
-rw-r--r--history-search/expando_test.pl58
-rw-r--r--history-search/frog_reload.pl99
-rw-r--r--history-search/help_a.pl15
-rw-r--r--history-search/help_b.pl15
-rw-r--r--history-search/key_test.pl100
-rw-r--r--history-search/prompt_info.pl77
-rw-r--r--history-search/rl_history_search.pl228
-rw-r--r--history-search/subtest.pl76
9 files changed, 695 insertions, 0 deletions
diff --git a/history-search/complete_test.pl b/history-search/complete_test.pl
new file mode 100644
index 0000000..a8ae485
--- /dev/null
+++ b/history-search/complete_test.pl
@@ -0,0 +1,27 @@
+use strict;
+use vars qw($VERSION %IRSSI);
+
+use Irssi;
+$VERSION = '2.1';
+%IRSSI = (
+ authors => 'Daenyth',
+ contact => 'Daenyth /at/ gmail /dot/ com',
+ name => 'Complete Last-Spoke',
+ description => 'When using tab completion on an empty input buffer, complete to the nick of the person who spoke most recently.',
+ license => 'GPL2',
+);
+
+sub do_complete {
+ my ($strings, $window, $word, $linestart, $want_space) = @_;
+ return unless ($linestart eq '' && $word eq '');
+
+# my $suffix = Irssi::settings_get_str('completion_char');
+# @$strings = $last_speaker . $suffix;
+ push @$strings, qw|/foo /bar /baz /bacon|;
+
+# $$want_space = 1;
+# Irssi::signal_stop();
+}
+
+ Irssi::signal_add_first( 'complete word', \&do_complete);
+
diff --git a/history-search/expando_test.pl b/history-search/expando_test.pl
new file mode 100644
index 0000000..0d5456a
--- /dev/null
+++ b/history-search/expando_test.pl
@@ -0,0 +1,58 @@
+use strict;
+use Irssi;
+use Irssi::TextUI; # for sbar_items_redraw
+
+use vars qw($VERSION %IRSSI);
+$VERSION = "1.0.1";
+%IRSSI = (
+ authors => "shabble",
+ contact => 'shabble+irssi@metavore.org, shabble@#irssi/Freenode',
+ name => "",
+ description => "",
+ license => "Public Domain",
+ changed => ""
+);
+
+my $prompt_additional_content = '';
+
+Irssi::expando_create('prompt_additional', \&expando_prompt, {});
+
+#TODO: necessary?
+#Irssi::signal_add_last 'gui print text finished' => \&redraw_prompts;
+
+sub expando_prompt {
+ my ($server, $witem, $arg) = @_;
+ return $prompt_additional_content;
+}
+
+sub redraw_prompts {
+ Irssi::statusbar_items_redraw ('prompt');
+ Irssi::statusbar_items_redraw ('prompt_empty');
+}
+
+sub handle_change_prompt_sig {
+ my ($text) = @_;
+
+ print "Got prompt change sig with: $text";
+
+ my $expanded_text = Irssi::parse_special($text);
+ my $changed = ($expanded_text ne $prompt_additional_content);
+
+ $prompt_additional_content = $expanded_text;
+
+ if ($changed) {
+ print "Redrawing prompts";
+ redraw_prompts();
+ }
+}
+
+sub prompt_additional_cmd {
+ my ($str) = @_;
+ print "Setting prompt to: $str";
+ Irssi::signal_emit('change prompt', $str);
+}
+
+Irssi::signal_register({'change prompt' => [qw/string/]});
+Irssi::signal_add('change prompt' => \&handle_change_prompt_sig);
+
+Irssi::command_bind('set_prompt' => \&prompt_additional_cmd);
diff --git a/history-search/frog_reload.pl b/history-search/frog_reload.pl
new file mode 100644
index 0000000..678c87d
--- /dev/null
+++ b/history-search/frog_reload.pl
@@ -0,0 +1,99 @@
+use strict;
+use warnings;
+
+use Irssi;
+use File::ChangeNotify();
+use File::Spec ();
+use File::Basename qw(basename);
+
+#my $THIS_SCRIPT = basename __FILE__;
+
+my $irssi_dir = Irssi::get_irssi_dir();
+my @watch_dirs = ($irssi_dir, $irssi_dir . '/scripts',
+ $irssi_dir . '/scripts/autorun');
+
+my $watcher = File::ChangeNotify->instantiate_watcher
+ (
+ directories => \@watch_dirs,
+ filter => qr/\.(?:pl|py)$/,
+ );
+
+my @watchers = File::ChangeNotify->usable_classes();
+print "Started reloader watching: ", join(", ", @watch_dirs), " using $watchers[0]";
+
+my %action_for = (
+ create => sub {
+ my ($path) = @_;
+ Irssi::print ("CREATE: Loading $path");
+ load_script($path);
+ },
+
+ modify => sub {
+ my ($path) = @_;
+ Irssi::print ("MODIFY: reloading $path");
+ reload($path);
+ },
+
+ delete => sub {
+ my ($path) = @_;
+ Irssi::print ("DELETE: Unloading $path");
+ unload_script($path);
+ },
+);
+
+#TODO: change me back.
+Irssi::timeout_add(3000, \&timer_sub, undef);
+
+sub timer_sub {
+ print "Timer sub called";
+ my @new_events = $watcher->new_events;
+ for my $event (@new_events) {
+
+ print "Handling event: ", $event->type, " path: ", $event->path;
+
+ if (my $callback = $action_for{$event->type}) {
+ $callback->($event->path);
+ }
+ }
+}
+
+sub reload {
+ my ($path) = @_;
+
+ unload_script($path);
+ load_script($path);
+}
+
+sub unload_script {
+ my ($script_path) = @_;
+ my $name = filepath_to_script($script_path);
+
+ if (script_is_loaded($name)) {
+ Irssi::print ("unloading $name...");
+ Irssi::command("script unload $name");
+ }
+}
+
+sub load_script {
+ my ($script_path) = @_;
+ Irssi::command("script load \"$script_path\"");
+}
+
+sub filepath_to_script {
+ my ($path) = @_;
+
+ my $name = basename $path;
+ $name =~ s/\.pl$//i;
+
+ return $name;
+}
+
+sub script_is_loaded {
+ my $name = shift;
+ print "Checking if $name is loaded";
+ no strict 'refs';
+ my $retval = defined %{ "Irssi::Script::${name}::" };
+ use strict 'refs';
+
+ return $retval;
+}
diff --git a/history-search/help_a.pl b/history-search/help_a.pl
new file mode 100644
index 0000000..53d902c
--- /dev/null
+++ b/history-search/help_a.pl
@@ -0,0 +1,15 @@
+use strict;
+use warnings;
+
+use Irssi;
+
+our $help = "this is help for a";
+
+Irssi::command_bind('help', sub {
+ if ($_[0] eq 'test_a') {
+ Irssi::print($help, MSGLEVEL_CLIENTCRAP);
+ Irssi::signal_stop();
+ return;
+ }
+ }
+);
diff --git a/history-search/help_b.pl b/history-search/help_b.pl
new file mode 100644
index 0000000..8b57a45
--- /dev/null
+++ b/history-search/help_b.pl
@@ -0,0 +1,15 @@
+use strict;
+use warnings;
+
+use Irssi;
+
+our $help = "this is help for b";
+
+Irssi::command_bind('help', sub {
+ if ($_[0] eq 'test_b') {
+ Irssi::print($help, MSGLEVEL_CLIENTCRAP);
+ Irssi::signal_stop();
+ return;
+ }
+ }
+);
diff --git a/history-search/key_test.pl b/history-search/key_test.pl
new file mode 100644
index 0000000..b16ff00
--- /dev/null
+++ b/history-search/key_test.pl
@@ -0,0 +1,100 @@
+use strict;
+use Irssi;
+use Irssi::TextUI; # for sbar_items_redraw
+
+use vars qw($VERSION %IRSSI);
+$VERSION = "1.0.1";
+%IRSSI = (
+ authors => "shabble",
+ contact => 'shabble+irssi@metavore.org, shabble@#irssi/Freenode',
+ name => "",
+ description => "",
+ license => "Public Domain",
+ changed => ""
+);
+
+
+Irssi::signal_add_last 'gui key pressed' => \&got_key;
+
+my $buf = '';
+
+sub got_key {
+ my ($key) = @_;
+ $buf .= " $key";
+ my $res = decode_keypress($key);
+ if (defined $res) {
+ print "codes: $buf";
+ print "Keypress: $res";
+ $buf = '';
+ }
+}
+
+# 1 means we've seen an esc, 2 means we've
+# seen an esc,[. 0 is normal.
+
+my $decoder_state = 0;
+
+sub decode_keypress {
+ my ($code) = @_;
+
+ if ($decoder_state == 1) {
+
+ # seen esc/meta.
+ if ($code == ord('[')) {
+ $decoder_state = 2;
+ return undef;
+ } else {
+ $decoder_state = 0;
+ return 'meta-' . chr($code);
+ }
+
+ } elsif ($decoder_state == 2) {
+
+ if ($code == ord('A')) {
+ $decoder_state = 0;
+ return 'up-arrow';
+ } elsif ($code == ord('B')) {
+ $decoder_state = 0;
+ return 'dn-arrow'
+ } elsif ($code == ord('C')) {
+ $decoder_state = 0;
+ return 'right-arrow'
+ } elsif ($code == ord('D')) {
+ $decoder_state = 0;
+ return 'left-arrow'
+ }
+
+ $decoder_state = 0;
+ return undef;
+
+ } else {
+
+ if ($code < 27) {
+
+ if ($code == 9) {
+ return 'tab';
+ }
+
+ return 'ctrl-' . chr($code + ord('a') -1);
+ }
+
+ if ($code > 32 && $code < 127) {
+ return chr($code);
+ }
+
+ if ($code == 32) {
+ return 'space';
+ }
+
+ if ($code == 127) {
+ return 'backspace';
+ }
+
+ if ($code == 27) {
+ $decoder_state = 1;
+ return undef;
+ }
+
+ return 'unknown ' . $code;
+ }
+}
diff --git a/history-search/prompt_info.pl b/history-search/prompt_info.pl
new file mode 100644
index 0000000..ad5321b
--- /dev/null
+++ b/history-search/prompt_info.pl
@@ -0,0 +1,77 @@
+# Usage:
+
+# edit your theme, find the line beginning:
+#
+# prompt = "..."
+#
+# and add the string `$prompt_additional' somewhere inside it.
+# If using the default: prompt = "[$*] ", then a good value would be:
+#
+# prompt = "[$*$prompt_additional] "
+#
+# Then add this script to your autorun directory (~/.irssi/scripts/autorun/)
+#
+# You can modify your prompt content by using the '/set_prompt <string>' command,
+# or from scripts by Irssi:signal_emit('change prompt', $string);
+
+use strict;
+use warnings;
+
+use Irssi;
+use Irssi::TextUI; # for sbar_items_redraw
+
+use vars qw($VERSION %IRSSI);
+$VERSION = "1.0.1";
+%IRSSI =
+ (
+ authors => "shabble",
+ contact => 'shabble+irssi@metavore.org, shabble@#irssi/Freenode',
+ name => "prompt_info",
+ description => "Helper script for dynamically adding text "
+ . "into the input-bar prompt.",
+ license => "Public Domain",
+ changed => "24/7/2010"
+ );
+
+sub DEBUG () { 0 }
+
+my $prompt_additional_content = '';
+
+Irssi::expando_create('prompt_additional', \&expando_prompt, {});
+
+sub expando_prompt {
+ my ($server, $witem, $arg) = @_;
+ return $prompt_additional_content;
+}
+
+sub redraw_prompts {
+ Irssi::statusbar_items_redraw ('prompt');
+ Irssi::statusbar_items_redraw ('prompt_empty');
+}
+
+sub handle_change_prompt_sig {
+ my ($text) = @_;
+
+ print "Got prompt change sig with: $text" if DEBUG;
+
+ my $expanded_text = Irssi::parse_special($text);
+ my $changed = ($expanded_text ne $prompt_additional_content);
+
+ $prompt_additional_content = $expanded_text;
+
+ if ($changed) {
+ print "Redrawing prompts" if DEBUG;
+ redraw_prompts();
+ }
+}
+
+sub prompt_additional_cmd {
+ my ($str) = @_;
+ print "Setting prompt to: $str" if DEBUG;
+ Irssi::signal_emit('change prompt', $str);
+}
+
+Irssi::signal_register({'change prompt' => [qw/string/]});
+Irssi::signal_add('change prompt' => \&handle_change_prompt_sig);
+
+Irssi::command_bind('set_prompt' => \&prompt_additional_cmd);
diff --git a/history-search/rl_history_search.pl b/history-search/rl_history_search.pl
new file mode 100644
index 0000000..9b58fd7
--- /dev/null
+++ b/history-search/rl_history_search.pl
@@ -0,0 +1,228 @@
+# Search within your typed history as you type (like ctrl-R in bash)
+# Usage:
+
+# * Setup: /bind ^R /history_search_start
+
+# * Then type ctrl-R and type what you're searching for
+
+# * You can cycle through multiple matches with ^R (older matches), and
+# ^S (newer matches)
+
+# * Hitting enter selects a match and terminates search mode.
+
+# * You can use ^G to exit search mode without selecting.
+
+
+# Original script Copyright 2007 Wouter Coekaerts <coekie@irssi.org>
+# Heavy modifications by Shabble <shabble+irssi@metavore.org>, 2010.
+
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+
+use strict;
+use Irssi;
+use Irssi::TextUI;
+use Data::Dumper;
+
+use vars qw($VERSION %IRSSI);
+$VERSION = '1.0';
+%IRSSI =
+ (
+ authors => 'Wouter Coekaerts, Tom Feist',
+ contact => 'coekie@irssi.org',
+ name => 'rl_history_search',
+ description => 'Search within your typed history as you type'
+ . ' (like ctrl-R in readline applications)',
+ license => 'GPLv2 or later',
+ url => 'http://wouter.coekaerts.be/irssi/',
+ changed => '24/7/2010'
+ );
+
+my $search_str = '';
+my $search_active = 0;
+
+my @history_cache = ();
+my @search_matches = ();
+my $match_index = 0;
+
+
+sub DEBUG () { 0 }
+
+# check we have prompt_info loaded.
+
+sub script_is_loaded {
+ my $name = shift;
+ print "Checking if $name is loaded" if DEBUG;
+ no strict 'refs';
+ my $retval = defined %{ "Irssi::Script::${name}::" };
+ use strict 'refs';
+
+ return $retval;
+}
+
+unless (script_is_loaded('prompt_info')) {
+ die "This script requires 'prompt_info' in order to work. "
+ . "Please load it and try again";
+} else {
+ history_init();
+}
+
+sub history_init {
+ Irssi::command_bind('history_search_start', \&history_search);
+ #Irssi::command_bind('history_search_exit', \&history_search_exit);
+ Irssi::signal_add_first('gui key pressed' => \&handle_keypress);
+}
+
+sub history_search {
+ $search_active = 1;
+ $search_str = '';
+ $match_index = -1;
+
+ @history_cache = Irssi::active_win()->get_history_lines();
+ @search_matches = ();
+
+ update_history_prompt();
+}
+
+sub history_exit {
+ $search_active = 0;
+ Irssi::signal_emit('change prompt', '');
+}
+
+sub update_history_prompt {
+ Irssi::signal_emit('change prompt', " reverse-i-search: \`$search_str'");
+}
+
+sub update_history_matches {
+ my ($match_str) = @_;
+ $match_str //= $search_str;
+
+ my %unique;
+ my @matches = grep { m/\Q$match_str/i } @history_cache;
+
+ @search_matches = ();
+
+ # uniquify the results, whilst maintaining order.
+ foreach my $m (@matches) {
+ unless (exists($unique{$m})) {
+ # add them in reverse order.
+ unshift @search_matches, $m;
+ }
+ $unique{$m}++;
+ }
+
+ print "updated matches: ", scalar(@search_matches), " ",
+ join(", ", @search_matches) if DEBUG;
+}
+
+sub get_history_match {
+ return $search_matches[$match_index];
+}
+
+sub prev_match {
+
+ $match_index++;
+ if ($match_index > $#search_matches) {
+ $match_index = 0;
+ }
+ print "index now: $match_index" if DEBUG;
+}
+
+sub next_match {
+
+ $match_index--;
+ if ($match_index < 0) {
+ $match_index = $#search_matches;
+ }
+ print "index now: $match_index" if DEBUG;
+}
+
+sub update_input {
+ my $match = get_history_match();
+ Irssi::gui_input_set($match);
+ Irssi::gui_input_set_pos(length $match);
+}
+
+sub handle_keypress {
+ my ($key) = @_;
+
+ return unless $search_active;
+
+ if ($key == 10) { # enter
+ print "selecting history and quitting" if DEBUG;
+ history_exit();
+ return;
+ }
+
+ if ($key == 18) { # Ctrl-R
+ print "skipping to prev match" if DEBUG;
+ prev_match();
+ update_input();
+ update_history_prompt();
+ Irssi::signal_stop(); # prevent the bind from being re-triggered.
+ return;
+ }
+
+ if ($key == 19) { # Ctrl-S
+ print "skipping to next match" if DEBUG;
+ next_match();
+ update_input();
+ update_history_prompt();
+
+ Irssi::signal_stop();
+ return;
+ }
+
+ if ($key == 7) { # Ctrl-G
+ print "aborting search" if DEBUG;
+ history_exit();
+
+ # cancel empties the inputline.
+ Irssi::gui_input_set('');
+ Irssi::gui_input_set_pos(0);
+
+ Irssi::signal_stop();
+ return;
+ }
+
+ if ($key == 127) { # DEL
+
+ if (length $search_str) {
+ $search_str = substr($search_str, 0, -1);
+ print "Deleting char, now: $search_str" if DEBUG;
+ }
+ update_history_matches();
+ update_history_prompt();
+
+ Irssi::signal_stop();
+ return;
+ }
+
+ # TODO: handle esc- sequences and arrow-keys?
+
+ if ($key >= 32) { # printable
+ $search_str .= chr($key);
+
+ update_history_matches();
+ update_history_prompt();
+ update_input();
+
+ Irssi::signal_stop();
+ return;
+ }
+
+ # any other key exits, for now.
+ history_exit();
+ #Irssi::signal_stop();
+}
diff --git a/history-search/subtest.pl b/history-search/subtest.pl
new file mode 100644
index 0000000..fd5a9cc
--- /dev/null
+++ b/history-search/subtest.pl
@@ -0,0 +1,76 @@
+use strict;
+use Irssi;
+use Irssi::TextUI;
+use Data::Dumper;
+
+use vars qw($VERSION %IRSSI);
+$VERSION = '1.0';
+%IRSSI = (
+ authors => 'Wouter Coekaerts',
+ contact => 'coekie@irssi.org',
+ name => 'history_search',
+ description => 'Search within your typed history as you type (like ctrl-R in bash)',
+ license => 'GPLv2 or later',
+ url => 'http://wouter.coekaerts.be/irssi/',
+ changed => '04/08/07'
+);
+
+
+Irssi::command_bind("foo bar", \&subcmd_bar);
+Irssi::command_bind("foo", \&subcmd_handler);
+
+sub subcmd_handler {
+ my ($data, $server, $item) = @_;
+ $data =~ s/\s+$//g;
+ Irssi::command_runsub('foo', $data, $server, $item);
+}
+
+sub subcmd_bar {
+ my ($args) = @_;
+ print "subcommand called with: $args";
+}
+
+# my $prev_typed;
+# my $prev_startpos;
+# my $enabled = 0;
+
+# Irssi::command_bind('history_search', sub {
+# $enabled = ! $enabled;
+# if ($enabled) {
+# $prev_typed = '';
+# $prev_startpos = 0;
+# }
+# });
+
+# Irssi::signal_add_last 'gui key pressed' => sub {
+# my ($key) = @_;
+
+# if ($key == 10) { # enter
+# $enabled = 0;
+# }
+
+# return unless $enabled;
+
+# my $prompt = Irssi::parse_special('$L');
+# my $pos = Irssi::gui_input_get_pos();
+
+# if ($pos < $prev_startpos) {
+# $enabled = 0;
+# return;
+# }
+
+# my $typed = substr($prompt, $prev_startpos, ($pos-$prev_startpos));
+
+# my $history = ($typed eq '') ? '' : Irssi::parse_special('$!' . $typed . '!');
+# if ($history eq '') {
+# $history = $typed;
+# }
+
+# my $startpos = index(lc($history), lc($typed));
+
+# Irssi::gui_input_set($history);
+# Irssi::gui_input_set_pos($startpos + length($typed));
+
+# $prev_typed = $typed;
+# $prev_startpos = $startpos;
+# };