aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTom Feist <shabble@metavore.org>2010-12-30 01:08:18 +0000
committerTom Feist <shabble@metavore.org>2010-12-30 01:08:18 +0000
commitd01a9573ada4b6a20ed506d10f0286754e738b08 (patch)
tree54da3d9c47bb78259d24900678af772207ac8112
parentido_switch: create hilight for numbers, and fix bugs with regex match impleme... (diff)
downloadirssi-scripts-d01a9573ada4b6a20ed506d10f0286754e738b08.tar.gz
irssi-scripts-d01a9573ada4b6a20ed506d10f0286754e738b08.zip
ido_switch: general refactor of code for more DRY. Beginning of full listing
available with <tab>.
-rw-r--r--ido-mode/ido_switcher.pl755
1 files changed, 471 insertions, 284 deletions
diff --git a/ido-mode/ido_switcher.pl b/ido-mode/ido_switcher.pl
index 3a6a99c..eca29ff 100644
--- a/ido-mode/ido_switcher.pl
+++ b/ido-mode/ido_switcher.pl
@@ -44,7 +44,7 @@ $VERSION = '2.0';
authors => 'Tom Feist, Wouter Coekaerts',
contact => 'shabble+irssi@metavore.org, shabble@#irssi/freenode',
name => 'ido_switcher',
- description => 'Select window(-items) using ido-mode like search interface',
+ description => 'Select window[-items] using an ido-mode like search interface',
license => 'GPLv2 or later',
url => 'http://github.com/shabble/irssi-scripts/tree/master/history-search/',
changed => '24/7/2010'
@@ -63,11 +63,13 @@ $VERSION = '2.0';
# TODO tab - display all possibilities in window (clean up afterwards)
# how exactly will this work?
# DONE sort by recent activity/recently used windows (separate commands?)
+# TODO should space auto-move forward to next window for easy stepping through
+# sequential/active windows?
my $input_copy = '';
my $input_pos_copy = 0;
-my $ido_switch_active = 0; # for intercepting keystrokes
+my $ido_switch_active = 0; # for intercepting keystrokes
my @window_cache = ();
my @search_matches = ();
@@ -76,6 +78,9 @@ my $match_index = 0;
my $search_str = '';
my $active_only = 0;
+my $mode_type = 'ALL';
+my @mode_cache;
+
my $need_clear = 0;
my $sort_ordering = "start-asc";
@@ -87,12 +92,15 @@ my $ido_use_flex;
my $DEBUG_ENABLED = 0;
sub DEBUG () { $DEBUG_ENABLED }
-#sub MODE_A () { 0 } # all
-#sub MODE_Q () { 1 } # queries
+
+sub MODE_WIN () { 0 } # windows
+sub MODE_NET () { 1 } # chatnets
#sub MODE_C () { 2 } # channels
#sub MODE_S () { 3 } # select server
#sub MODE_W () { 4 } # select window
+my $MODE = MODE_WIN;
+
# check we have uberprompt loaded.
sub _print {
@@ -117,23 +125,59 @@ sub _print_clear {
sub print_all_matches {
my $msg = join(", ", map { $_->{name} } @search_matches);
- _print($msg);
-}
+ my $message_header = "Windows:";
+ my $win = Irssi::active_win();
+ my $win_width = $win->{width} || 80;
+
+ # TODO: needs to prefix ambig things with chatnet, or maybe order in groups
+ # by chatnet with newlines.
+
+ # Also, colourise the channel list.
+
+ my $col_width;
+
+ for (@search_matches) {
+ my $len = length($_->{name});
+ $col_width = $len if $len > $col_width;
+ }
+
+ my $cols = int($win_width / $col_width);
+
+ my @lines;
+ my $i = 0;
+ my @line;
-sub script_is_loaded {
- my $name = shift;
- _debug_print "Checking if $name is loaded";
- no strict 'refs';
- my $retval = defined %{ "Irssi::Script::${name}::" };
- use strict 'refs';
+ for my $item (@search_matches) {
+ my $name = $item->{name};
+ push @line, sprintf('%.*s', $col_width, $name);
+ if ($i == $cols) {
+ push @lines, join ' ', @line;
+ @line = ();
+ $i = 0;
+ }
+ }
+ # flush rest out.
+ push @lines, join ' ', @line;
- return $retval;
+ _print($message_header);
+ _print($_) for (@lines);
+ #_print("Longtest name: $longest_name");
}
+ sub script_is_loaded {
+ my $name = shift;
+ _debug_print "Checking if $name is loaded";
+ no strict 'refs';
+ my $retval = defined %{ "Irssi::Script::${name}::" };
+ use strict 'refs';
+
+ return $retval;
+ }
+
unless (script_is_loaded('uberprompt')) {
_print "This script requires 'uberprompt.pl' in order to work. "
- . "Attempting to load it now...";
+ . "Attempting to load it now...";
Irssi::signal_add('script error', 'load_uberprompt_failed');
Irssi::command("script load uberprompt.pl");
@@ -147,7 +191,7 @@ unless (script_is_loaded('uberprompt')) {
sub load_uberprompt_failed {
Irssi::signal_remove('script error', 'load_uberprompt_failed');
_print "Script could not be loaded. Script cannot continue. "
- . "Check you have uberprompt.pl installed in your path and "
+ . "Check you have uberprompt.pl installed in your path and "
. "try again.";
die "Script Load Failed: " . join(" ", @_);
}
@@ -183,6 +227,7 @@ sub ido_switch_start {
$ido_switch_active = 1;
$search_str = '';
$match_index = 0;
+ $mode_type = 'ALL';
# refresh in case we toggled it last time.
$ido_use_flex = Irssi::settings_get_bool('ido_use_flex');
@@ -193,13 +238,44 @@ sub ido_switch_start {
_update_cache();
update_matches();
- update_prompt();
+ update_window_select_prompt();
}
sub _update_cache {
@window_cache = get_all_windows();
}
+sub _build_win_obj {
+ my ($win, $win_item) = @_;
+
+ my @base = (
+ b_pos => -1,
+ e_pos => -1,
+ hilight_field => 'name',
+ active => $win->{data_level} > 0,
+ num => $win->{refnum},
+ server => $win->{active_server},
+
+ );
+
+ if (defined($win_item)) {
+ return (
+ @base,
+ name => $win_item->{visible_name},
+ type => $win_item->{type},
+ itemname => $win_item->{name},
+ active => $win_item->{data_level} > 0,
+
+ )
+ } else {
+ return (
+ @base,
+ name => $win->{name},
+ type => 'WIN',
+ );
+ }
+}
+
sub get_all_windows {
my @ret;
@@ -208,394 +284,505 @@ sub get_all_windows {
if ($win->{name} ne '') {
_debug_print "Adding window: " . $win->{name};
- push @ret, {
- name => $win->{name},
- type => 'WINDOW',
- num => $win->{refnum},
- server => $win->{active_server},
- active => $win->{data_level} > 0,
- b_pos => -1,
- e_pos => -1,
- hilight_field => 'name',
- };
+ push @ret, { _build_win_obj($win, undef) };
}
-
if (scalar @items) {
foreach my $item (@items) {
_debug_print "Adding windowitem: " . $item->{visible_name};
-
- push @ret, {
- name => $item->{visible_name},
- type => $item->{type},
- server => $item->{server},
- num => $win->{refnum},
- itemname => $item->{name},
- active => $win->{data_level} > 0,
- b_pos => -1,
- e_pos => -1,
- hilight_field => 'name',
- };
+ push @ret, { _build_win_obj($win, $item) };
}
} else {
- #_debug_print "Error occurred reading info from window: $win";
+ _debug_print "Error occurred reading info from window: $win";
#_debug_print Dumper($win);
}
}
-
@ret = _sort_windows(\@ret);
return @ret;
+
}
-sub _sort_windows {
- my $list_ref = shift;
- my @ret = @$list_ref;
+ sub _sort_windows {
+ my $list_ref = shift;
+ my @ret = @$list_ref;
- @ret = sort { $a->{num} <=> $b->{num} } @ret;
+ @ret = sort { $a->{num} <=> $b->{num} } @ret;
- return @ret;
-}
+ return @ret;
+ }
-sub ido_switch_select {
- my ($selected, $is_refnum) = @_;
+ sub ido_switch_select {
+ my ($selected, $is_refnum) = @_;
- _debug_print "Selecting window: " . $selected->{name};
+ _debug_print "Selecting window: " . $selected->{name};
- Irssi::command("WINDOW GOTO " . $selected->{name});
+ Irssi::command("WINDOW GOTO " . $selected->{name});
+
+ if ($selected->{type} ne 'WINDOW') {
+ _debug_print "Selecting window item: " . $selected->{itemname};
+ Irssi::command("WINDOW ITEM GOTO " . $selected->{itemname});
+ }
- if ($selected->{type} ne 'WINDOW') {
- _debug_print "Selecting window item: " . $selected->{itemname};
- Irssi::command("WINDOW ITEM GOTO " . $selected->{itemname});
}
-}
+ sub ido_switch_exit {
+ $ido_switch_active = 0;
-sub ido_switch_exit {
- $ido_switch_active = 0;
+ _print_clear();
- _print_clear();
+ Irssi::gui_input_set($input_copy);
+ Irssi::gui_input_set_pos($input_pos_copy);
+ Irssi::signal_emit('change prompt', '', 'UP_INNER');
+ }
- Irssi::gui_input_set($input_copy);
- Irssi::gui_input_set_pos($input_pos_copy);
- Irssi::signal_emit('change prompt', '', 'UP_INNER');
-}
+ sub _order_matches {
+ return @_[$match_index .. $#_,
+ 0 .. $match_index - 1]
+ }
-sub _order_matches {
- return @_[$match_index .. $#_,
- 0 .. $match_index - 1]
-}
+ sub update_window_select_prompt {
+
+ # take the top $ido_show_count entries and display them.
+ my $match_count = scalar @search_matches;
+ my $show_count = $ido_show_count;
+ my $match_string = '[No match';
+
+ $show_count = $match_count if $match_count < $show_count;
+
+ if ($show_count > 0) { # otherwise, default message above.
+ _debug_print "Showing: $show_count matches";
+
+ my @ordered_matches = _order_matches(@search_matches);
+
+ my %uniq;
+ # determine which items are non-unique, if any.
+ foreach my $res (@ordered_matches) {
+ my $name = $res->{name};
+
+ if (exists $uniq{$name}) {
+ push @{$uniq{$name}}, $res;
+ } else {
+ $uniq{$name} = [];
+ push @{$uniq{$name}}, $res;
+ }
+ }
+
+ # and set a flag to ensure they have their network tag applied
+ # to them when drawn.
+ foreach my $name (keys %uniq) {
+ my @values = @{$uniq{$name}};
+ if (@values > 1) {
+ $_->{display_net} = 1 for @values;
+ }
+ }
-sub update_prompt {
+ #
+ my @display = @ordered_matches[0..$show_count - 1];
- #TODO: refactor this beast.
+ # show the first entry in green
- # take the top $ido_show_count entries and display them.
- my $match_count = scalar @search_matches;
- my $show_count = $ido_show_count;
- my $match_string = '(no matches) ';
+ my $first = shift @display;
+ my $formatted_first = _format_display_entry($first, '%g');
+ unshift @display, $formatted_first;
- $show_count = $match_count if $match_count < $show_count;
+ # and array-slice-map the rest to be red.
+ # or yellow, if they have unviewed activity
- if ($show_count > 0) {
- _debug_print "Showing: $show_count matches";
+ @display[1..$#display]
+ = map
+ {
+ _format_display_entry($_, $_->{active}?'%y':'%r')
- my @ordered_matches = _order_matches(@search_matches);
- my @display = @ordered_matches[0..$show_count - 1];
+ } @display[1..$#display];
+
+ # join em all up
+ $match_string = join ', ', @display;
+ }
- # show the first entry in green
+ my @indicators;
- unshift(@display, _format_display_entry(shift(@display), '%g'));
+ # indicator if flex mode is being used (C-f to toggle)
+ push @indicators, $ido_use_flex ? 'Flex' : 'Exact';
+ push @indicators, 'Active' if $active_only;
+ push @indicators, ucfirst(lc($mode_type));
- # and array-slice-map the rest to be red.
- @display[1..$#display]
- = map { _format_display_entry($_, '%r') } @display[1..$#display];
+ my $flex = sprintf(' %%k[%%n%s%%k]%%n ', join ',', @indicators);
- # join em all up
- $match_string = join ', ', @display;
+ my $search = '';
+ $search = (sprintf '`%s\': ', $search_str) if length $search_str;
+
+ Irssi::signal_emit('change prompt', $flex . $search . $match_string,
+ 'UP_INNER');
}
- # indicator if flex mode is being used (C-f to toggle)
- my @indicators = ($ido_use_flex ? 'Flex' : 'Exact');
- push @indicators, 'Active' if $active_only;
- my $flex = sprintf(' %%k[%%n%s%%k]%%n ', join ',', @indicators);
- my $search = '';
- $search = (sprintf '`%s\': ', $search_str) if length $search_str;
+ sub _format_display_entry {
+ my ($obj, $colour) = @_;
- Irssi::signal_emit('change prompt', $flex . $search . $match_string,
- 'UP_INNER');
-}
+ my $field = $obj->{hilight_field};
+ my $hilighted = { name => $obj->{name}, num => $obj->{num} };
+ my $show_tag = $obj->{display_net} || 0;
-sub _format_display_entry {
- my ($obj, $colour) = @_;
+ if ($obj->{b_pos} >= 0 && $obj->{e_pos} > $obj->{b_pos}) {
+ substr($hilighted->{$field}, $obj->{e_pos}, 0) = '%_';
+ substr($hilighted->{$field}, $obj->{b_pos}, 0) = '%_';
+ _debug_print "Showing $field as: " . $hilighted->{$field}
+ }
- my $field = $obj->{hilight_field};
- my $hilighted = { name => $obj->{name}, num => $obj->{num} };
+ return sprintf('%s%s:%s%s%%n',
+ $colour,
+ $hilighted->{num},
+ $show_tag ? _format_display_tag($obj) : '',
+ $hilighted->{name});
+ }
- if ($obj->{b_pos} >= 0 && $obj->{e_pos} > $obj->{b_pos}) {
- substr($hilighted->{$field}, $obj->{e_pos}, 0) = '%_';
- substr($hilighted->{$field}, $obj->{b_pos}, 0) = '%_';
- _debug_print "Showing $field as: " . $hilighted->{$field}
+ sub _format_display_tag {
+ my $obj = shift;
+ if (defined $obj->{server}) {
+ my $server = $obj->{server};
+ my $tag = $server->{tag};
+ return $tag . '/' if length $tag;
+ }
+ return '';
}
- return sprintf('%s%s:%s%%n', $colour, $hilighted->{num}, $hilighted->{name});
-}
+ sub _check_active {
+ my ($obj) = @_;
+ return 1 unless $active_only;
+ return $obj->{active};
+ }
-sub _check_active {
- my ($obj) = @_;
- return 1 unless $active_only;
- return $obj->{active};
-}
+ sub update_matches {
-sub update_matches {
+ _update_cache() unless $search_str;
- _update_cache() unless $search_str;
+ if ($mode_type ne 'ALL') {
+ @mode_cache = @window_cache;
+ @window_cache = grep { print "Type: " . $_->{type}; $_->{type} eq $mode_type } @window_cache;
+ } else {
+ @window_cache = @mode_cache if @mode_cache;
+ }
- if ($search_str =~ m/^\d+$/) {
+ if ($search_str =~ m/^\d+$/) {
- @search_matches =
- grep {
- _check_active($_) and regex_match($_, 'num')
- } @window_cache;
+ @search_matches =
+ grep {
+ _check_active($_) and regex_match($_, 'num')
+ } @window_cache;
- } elsif ($ido_use_flex) {
+ } elsif ($ido_use_flex) {
- @search_matches =
- grep {
- _check_active($_) and flex_match($_) >= 0
- } @window_cache;
+ @search_matches =
+ grep {
+ _check_active($_) and flex_match($_) >= 0
+ } @window_cache;
- } else {
+ } else {
- @search_matches =
- grep {
- _check_active($_) and regex_match($_, 'name')
- } @window_cache;
- }
+ @search_matches =
+ grep {
+ _check_active($_) and regex_match($_, 'name')
+ } @window_cache;
+ }
-}
+ }
-sub regex_match {
- my ($obj, $field) = @_;
- if ($obj->{$field} =~ m/^(.*?)\Q$search_str\E(.*?)$/i) {
- $obj->{hilight_field} = $field;
- $obj->{b_pos} = length $1;
- $obj->{e_pos} = $obj->{b_pos} + length($search_str);
- return 1;
+ sub regex_match {
+ my ($obj, $field) = @_;
+ if ($obj->{$field} =~ m/^(.*?)\Q$search_str\E(.*?)$/i) {
+ $obj->{hilight_field} = $field;
+ $obj->{b_pos} = length $1;
+ $obj->{e_pos} = $obj->{b_pos} + length($search_str);
+ return 1;
+ }
+ return 0;
}
- return 0;
-}
-sub flex_match {
- my ($obj) = @_;
+ sub flex_match {
+ my ($obj) = @_;
- my $pattern = $search_str;
- my $source = $obj->{name};
+ my $pattern = $search_str;
+ my $source = $obj->{name};
- _debug_print "Flex match: $pattern / $source";
+ _debug_print "Flex match: $pattern / $source";
- # default to matching everything if we don't have a pattern to compare
- # against.
+ # default to matching everything if we don't have a pattern to compare
+ # against.
- return 0 unless $pattern;
+ return 0 unless $pattern;
- my @chars = split '', lc($pattern);
- my $ret = -1;
- my $first = 0;
+ my @chars = split '', lc($pattern);
+ my $ret = -1;
+ my $first = 0;
- my $lc_source = lc($source);
+ my $lc_source = lc($source);
- $obj->{hilight_field} = 'name';
+ $obj->{hilight_field} = 'name';
- foreach my $char (@chars) {
- my $pos = index($lc_source, $char, $ret);
- if ($pos > -1) {
+ foreach my $char (@chars) {
+ my $pos = index($lc_source, $char, $ret);
+ if ($pos > -1) {
- # store the beginning of the match
- $obj->{b_pos} = $pos unless $first;
- $first = 1;
+ # store the beginning of the match
+ $obj->{b_pos} = $pos unless $first;
+ $first = 1;
- _debug_print("matched: $char at $pos in $source");
- $ret = $pos + 1;
+ _debug_print("matched: $char at $pos in $source");
+ $ret = $pos + 1;
- } else {
+ } else {
- $obj->{b_pos} = $obj->{e_pos} = -1;
- _debug_print "Flex returning: -1";
+ $obj->{b_pos} = $obj->{e_pos} = -1;
+ _debug_print "Flex returning: -1";
- return -1;
+ return -1;
+ }
}
- }
- _debug_print "Flex returning: $ret";
+ _debug_print "Flex returning: $ret";
- #store the end of the match.
- $obj->{e_pos} = $ret;
+ #store the end of the match.
+ $obj->{e_pos} = $ret;
- return $ret;
-}
+ return $ret;
+ }
-sub prev_match {
+ sub prev_match {
- $match_index++;
- if ($match_index > $#search_matches) {
- $match_index = 0;
+ $match_index++;
+ if ($match_index > $#search_matches) {
+ $match_index = 0;
+ }
+
+ _debug_print "index now: $match_index";
}
- _debug_print "index now: $match_index";
-}
+ sub next_match {
-sub next_match {
+ $match_index--;
+ if ($match_index < 0) {
+ $match_index = $#search_matches;
+ }
+ _debug_print "index now: $match_index";
+ }
- $match_index--;
- if ($match_index < 0) {
- $match_index = $#search_matches;
+ sub get_window_match {
+ return $search_matches[$match_index];
}
- _debug_print "index now: $match_index";
-}
-sub get_window_match {
- return $search_matches[$match_index];
-}
+ sub handle_keypress {
+ my ($key) = @_;
-sub handle_keypress {
- my ($key) = @_;
+ return unless $ido_switch_active;
- return unless $ido_switch_active;
+ if ($key == 0) { # C-SPC?
+ _debug_print "\%_Ctrl-space\%_";
- if ($key == 0) { # C-SPC?
- _debug_print "\%_Ctrl-space\%_";
+ $search_str = '';
+ @window_cache = @search_matches;
+ update_window_select_prompt();
- $search_str = '';
- @window_cache = @search_matches;
- update_prompt();
+ Irssi::signal_stop();
+ return;
+ }
- Irssi::signal_stop();
- return;
- }
+ if ($key == 3) { # C-c
+ _print_clear();
+ Irssi::signal_stop();
+ return;
+ }
+ if ($key == 4) { # C-d
+ update_network_select_prompt();
+ Irssi::signal_stop();
+ return;
+ }
- if ($key == 3) { # C-C
- _print_clear();
- Irssi::signal_stop();
- return;
- }
+ if ($key == 5) { # C-e
+ $active_only = not $active_only;
+ Irssi::signal_stop();
+ update_matches();
+ update_window_select_prompt();
+ return;
+ }
- if ($key == 5) { # C-e
- $active_only = not $active_only;
- Irssi::signal_stop();
- update_matches();
- update_prompt();
- return;
- }
+ if ($key == 6) { # C-f
- if ($key == 6) { # C-f
+ $ido_use_flex = not $ido_use_flex;
+ _update_cache();
- $ido_use_flex = not $ido_use_flex;
- _update_cache();
+ update_matches();
+ update_window_select_prompt();
- update_matches();
- update_prompt();
+ Irssi::signal_stop();
+ return;
+ }
+ if ($key == 9) { # TAB
+ _debug_print "Tab complete";
+ print_all_matches();
+ Irssi::signal_stop();
+ }
- Irssi::signal_stop();
- return;
- }
- if ($key == 9) { # TAB
- _debug_print "Tab complete";
- print_all_matches();
- Irssi::signal_stop();
- }
+ if ($key == 10) { # enter
+ _debug_print "selecting history and quitting";
+ my $selected_win = get_window_match();
+ ido_switch_select($selected_win);
- if ($key == 10) { # enter
- _debug_print "selecting history and quitting";
- my $selected_win = get_window_match();
- ido_switch_select($selected_win);
+ ido_switch_exit();
+ Irssi::signal_stop();
+ return;
+ }
- ido_switch_exit();
- Irssi::signal_stop();
- return;
- }
+ if ($key == 18) { # Ctrl-R
+ _debug_print "skipping to prev match";
+ #update_matches();
+ next_match();
- if ($key == 18) { # Ctrl-R
- _debug_print "skipping to prev match";
- #update_matches();
- next_match();
+ update_window_select_prompt();
+ Irssi::signal_stop(); # prevent the bind from being re-triggered.
+ return;
+ }
- update_prompt();
- Irssi::signal_stop(); # prevent the bind from being re-triggered.
- return;
- }
+ if ($key == 17) { # Ctrl-q
+ if ($mode_type eq 'CHANNEL') {
+ $mode_type = 'QUERY';
+ } elsif ($mode_type eq 'QUERY') {
+ $mode_type = 'ALL';
+ } else { # ALL
+ $mode_type = 'CHANNEL';
+ }
+ update_matches();
+ update_window_select_prompt();
+ Irssi::signal_stop();
+ }
- if ($key == 19) { # Ctrl-S
- _debug_print "skipping to next match";
- prev_match();
+ if ($key == 19) { # Ctrl-s
+ _debug_print "skipping to next match";
+ prev_match();
- #update_matches();
- update_prompt();
+ #update_matches();
+ update_window_select_prompt();
- Irssi::signal_stop();
- return;
- }
+ Irssi::signal_stop();
+ return;
+ }
- if ($key == 7) { # Ctrl-G
- _debug_print "aborting search";
- ido_switch_exit();
- Irssi::signal_stop();
- return;
- }
+ if ($key == 7) { # Ctrl-g
+ _debug_print "aborting search";
+ ido_switch_exit();
+ Irssi::signal_stop();
+ return;
+ }
- if ($key == 21) { # Ctrl-U
- $search_str = '';
- update_matches();
- update_prompt();
+ if ($key == 21) { # Ctrl-u
+ $search_str = '';
+ update_matches();
+ update_window_select_prompt();
- Irssi::signal_stop();
- return;
+ Irssi::signal_stop();
+ return;
- }
+ }
+
+ if ($key == 127) { # DEL
+
+ if (length $search_str) {
+ $search_str = substr($search_str, 0, -1);
+ _debug_print "Deleting char, now: $search_str";
+ }
- if ($key == 127) { # DEL
+ update_matches();
+ update_window_select_prompt();
- if (length $search_str) {
- $search_str = substr($search_str, 0, -1);
- _debug_print "Deleting char, now: $search_str";
+ Irssi::signal_stop();
+ return;
}
- update_matches();
- update_prompt();
+ # TODO: handle esc- sequences and arrow-keys?
+
+ if ($key == 27) { # Esc
+ ido_switch_exit();
+ return;
+ }
+
+ if ($key == 32) { # space
+ my $selected_win = get_window_match();
+ ido_switch_select($selected_win);
+ Irssi::signal_stop();
+
+ return;
+ }
+
+ if ($key > 32) { # printable
+ $search_str .= chr($key);
+
+ update_matches();
+ update_window_select_prompt();
+
+ Irssi::signal_stop();
+ return;
+ }
+ # ignore all other keys.
Irssi::signal_stop();
- return;
}
- # TODO: handle esc- sequences and arrow-keys?
+ ido_switch_init();
- if ($key == 27) { # Esc
- ido_switch_exit();
- return;
- }
+ sub update_network_select_prompt {
- if ($key == 32) { # space
- my $selected_win = get_window_match();
- ido_switch_select($selected_win);
- Irssi::signal_stop();
+ my @servers = map
+ {
+ {
+ name => $_->{tag},
+ type => 'SERVER',
+ active => 0,
+ e_pos => -1,
+ b_pos => -1,
+ hilight_field => 'name',
+ }
+ } Irssi::servers();
- return;
- }
+ my $match_count = scalar @servers;
+ my $show_count = $ido_show_count;
+ my $match_string = '(no matches) ';
- if ($key > 32) { # printable
- $search_str .= chr($key);
+ $show_count = $match_count if $match_count < $show_count;
- update_matches();
- update_prompt();
+ if ($show_count > 0) {
+ _debug_print "Showing: $show_count matches";
- Irssi::signal_stop();
- return;
- }
+ my @ordered_matches = _order_matches(@servers);
+ my @display = @ordered_matches[0..$show_count - 1];
- # ignore all other keys.
- Irssi::signal_stop();
-}
+ # show the first entry in green
+
+ unshift(@display, _format_display_entry(shift(@display), '%g'));
+
+ # and array-slice-map the rest to be red (or yellow for active)
+ @display[1..$#display]
+ = map
+ {
+ _format_display_entry($_, $_->{active}?'%y':'%r')
-ido_switch_init();
+ } @display[1..$#display];
+ # join em all up
+ $match_string = join ', ', @display;
+ }
+
+ my @indicators;
+
+ # indicator if flex mode is being used (C-f to toggle)
+ push @indicators, $ido_use_flex ? 'Flex' : 'Exact';
+ push @indicators, 'Active' if $active_only;
+
+ my $flex = sprintf(' %%k[%%n%s%%k]%%n ', join ',', @indicators);
+
+ my $search = '';
+ $search = (sprintf '`%s\': ', $search_str) if length $search_str;
+
+ Irssi::signal_emit('change prompt', $flex . $search . $match_string,
+ 'UP_INNER');
+
+ }