use strict;
use warnings;

# Completers for client state

package BarnOwl::Complete::Client;

use BarnOwl::Completion::Util qw(complete_flags);
use BarnOwl::Complete::Filter qw(complete_filter_name complete_filter_expr);

my @all_colors = qw(default
                    black
                    blue
                    cyan
                    green
                    magenta
                    red
                    white
                    yellow);

my %show = (
    information => undef,
    colors      => undef,
    commands    => undef,
    command     => \&complete_command,
    errors      => undef,
    filters     => undef,
    filter      => \&complete_filter_name,
    license     => undef,
    keymaps     => undef,
    keymap      => \&complete_keymap,
    quickstart  => undef,
    startup     => undef,
    status      => undef,
    styles      => undef,
    subscriptions       => undef,
    subs        => undef,
    terminal    => undef,
    variables   => undef,
    variable    => \&complete_variable,
    version     => undef,
    view        => undef,
    zpunts      => undef,
   );

sub complete_command { return sort @BarnOwl::all_commands; }
sub complete_color { return @all_colors; }
sub complete_variable    { return @{BarnOwl::all_variables()}; }
sub complete_style       { return @{BarnOwl::all_styles()}; }
sub complete_keymap      { return @{BarnOwl::all_keymaps()}; }

sub complete_help {
    my $ctx = shift;
    if($ctx->word == 1) {
        return complete_command();
    }
}

sub complete_show {
    my $ctx = shift;
    if($ctx->word == 1) {
        return keys %show;
    } elsif ($ctx->word == 2) {
        my $cmd = $show{$ctx->words->[1]};
        if($cmd) {
            return $cmd->($ctx);
        }
    }
}

sub complete_filter {
    my $ctx = shift;
    # Syntax: filter FILTERNAME FLAGS EXPR

    # FILTERNAME
    return complete_filter_name() if $ctx->word == 1;

    # FLAGS
    $ctx = $ctx->shift_words(1); # complete_flags starts at the second word
    return complete_flags($ctx,
        [qw()],
        {
           "-c" => \&complete_color,
           "-b" => \&complete_color,
        },
        # EXPR
        sub {
            my $ctx = shift;
            my $arg = shift;

            # We pass stop_at_nonflag, so we can rewind to the start
            my $idx = $ctx->word - $arg;
            $ctx = $ctx->shift_words($idx);
            return complete_filter_expr($ctx);
        },
        stop_at_nonflag => 1
        );
}

sub complete_view {
    my $ctx = shift;
    if ($ctx->word == 1) {
        return ("--home", "-d", "-r", "-s", complete_filter_name());
    }
    if ($ctx->words->[1] eq "--home") {
        return;
    }
    if ($ctx->words->[1] eq "-d") {
        $ctx = $ctx->shift_words(2);
        return complete_filter_expr($ctx);
    }
    if ($ctx->words->[1] eq "-s") {
        return complete_style();
    }
    return;
}

sub complete_getvar {
    my $ctx = shift;
    return unless ($ctx->word == 1);
    return complete_variable();
}

sub complete_set {
    my $ctx = shift;
    return complete_flags($ctx,
        [qw(-q)],
        {
        },
         \&complete_set_args
        );
}
sub complete_set_args {
    my $ctx = shift;
    my $arg = shift;
    return if $arg;
    return complete_variable();
}

sub complete_startup {
    my $ctx = shift;
    my $new_ctx = $ctx->shift_words(1);
    return BarnOwl::Completion::get_completions($new_ctx);
}

BarnOwl::Completion::register_completer(help    => \&complete_help);
BarnOwl::Completion::register_completer(filter  => \&complete_filter);
BarnOwl::Completion::register_completer(view    => \&complete_view);
BarnOwl::Completion::register_completer(show    => \&complete_show);
BarnOwl::Completion::register_completer(getvar  => \&complete_getvar);
BarnOwl::Completion::register_completer(set     => \&complete_set);
BarnOwl::Completion::register_completer(unset   => \&complete_set);
BarnOwl::Completion::register_completer(startup => \&complete_startup);

1;
