package Uploader::GUI::wxCategoryTreeCtrl;
use strict;
use Wx;
use Wx::DND;
use base qw/Wx::TreeCtrl Class::Accessor::Fast/;

use Wx qw/
    wxTheApp
    wxBITMAP_TYPE_PNG
    wxDefaultPosition
    wxDefaultSize
    wxALIGN_CENTER
    wxALL
    wxSWISS
    wxNORMAL
    wxVERTICAL
    wxBOLD
    wxWHITE
    wxID_CANCEL
/;

__PACKAGE__->mk_accessors( 
    qw/
          wx_img
          categories
          root
          selection_ids
          frame_callback
      / 
);
use Data::Dumper;


sub new {
    my( $class, $params ) = @_;
  
    my( $self ) = $class->SUPER::new(
        $params->{parentwnd},
        $params->{id}||-1,
        $params->{position}||wxDefaultPosition,
        $params->{size}||[ -1, -1],
    );
    
    $self->categories(
        $params->{categories}
    );

    $self->selection_ids(
        $params->{selection_ids}
    );

    $self->frame_callback(
        $params->{frame_callback}
    );


    $self->init_bitmaps;
    $self->init_empty_category_msg;
    $self->init_empty_category_evt;

    if(wxTheApp->use_offline){
        $self->Enable(0);
    }
    else{
        $self->Populate;
    }


    $self;
}


sub ShowEmptyMsg {
    my ( $self ) = @_;

    $self->{_empty_panel}->Show;
}


sub HideEmptyMsg {
    my ( $self ) = @_;

    $self->{_empty_panel}->Hide;
}


sub init_bitmaps{
    my ( $self ) = @_;

    $self->wx_img(
        Wx::ImageList->new( 16, 16, 1 )
    );


    map {
        $self->wx_img->Add(
            Wx::Bitmap->new( $_, wxBITMAP_TYPE_PNG )
        );
    }
    (
        wxTheApp->resource_path('tree_pwg.png'),
        wxTheApp->resource_path('tree_folder.png'),
    );

    $self->SetImageList( $self->wx_img );
}


sub itemData { Wx::TreeItemData->new( $_[0] ) }


sub Populate {
    my ( $self ) = @_;
    
    my $tree_items = $self->categories;
    my $root = shift @{$tree_items};

    $self->root(
        $self->AddRoot( 
            $root->[0], 
            $root->[3], 
            $root->[4], 
            itemData( $root->[2] ) 
        )
    );

  $self->populate_tree_helper( $self->root, $tree_items );
  
  $self->Expand( $self->root );
}

sub populate_tree_helper {
  my ( $self, $parent_id, $tree_items ) = @_;

  my $id;

  map {
      my $name = $_->[0];

      $id = $self->AppendItem( 
                                   $parent_id, 
                                   $name,
                                   defined($_->[3]) ? $_->[3] : 0, 
                                   defined($_->[4]) ? $_->[4] : 0, 
                                   itemData( $_->[2]) 
                              );
      # current item has children
      if( ref( $_->[1] ) eq 'ARRAY' ) {
          $self->populate_tree_helper( $id, $_->[1] );
      } 
  }
  @{$tree_items};

}


sub init_empty_category_msg {

    my ( $self ) = @_;
    # add a panel
    my $empty_panel = Wx::Panel->new($self, -1, wxDefaultPosition, wxDefaultSize);
    my( $item0 ) = Wx::BoxSizer->new( wxVERTICAL );
    
    my $fb = Wx::Font->new( 12, wxSWISS, wxNORMAL, wxBOLD );


    my( $item1 ) = Wx::Button->new(
        $empty_panel,
        $main::CATEGORIES_ADD,
        wxTheApp->branding->{'Add new category'},
        wxDefaultPosition,
        [-1,40],
        0
    );
    my $btfont = Wx::Font->new(12, wxSWISS, wxNORMAL, wxNORMAL );
    $item1->SetFont($btfont);
    $item0->AddWindow( $item1, 0, wxALIGN_CENTER|wxALL, 5 );


    $empty_panel->SetSizer( $item0 );
    $item0->SetSizeHints( $empty_panel );

    $self->{_empty_panel} = $empty_panel;
    $self->{_empty_panel}->SetBackgroundColour(wxWHITE);

    my ($wp, $hp) = $self->{_empty_panel}->GetSizeWH;

    $self->SetMinSize( [20+$wp, -1 ]);

    Wx::Event::EVT_BUTTON( $self, $main::CATEGORIES_ADD, \&AddCategory );
}


sub init_empty_category_evt{
    my ( $self ) = @_;

    Wx::Event::EVT_PAINT( $self, sub {
            my ( $tree, $event ) = @_;
            if(exists $tree->{_empty_panel} and ! exists $tree->{_empty_panel}{_paint}){
                my ($w, $h) = $tree->GetSizeWH;
                my ($x, $y) = $tree->{_empty_panel}->GetPositionXY;

                $tree->{_empty_panel}{x} = $x if !exists $tree->{_empty_panel}{x} ;
                $tree->{_empty_panel}{y} = $y if !exists $tree->{_empty_panel}{y};
                my ($wp, $hp) = $tree->{_empty_panel}->GetSizeWH;
                my $x_off = ($w-$wp)/2 > 0 ? ($w-$wp)/2 : 0;
                my $y_off = ($h-$hp)/2 > 0 ? ($h-$hp)/2 : 0;
                $tree->{_empty_panel}->Move(
                    [
                        $tree->{_empty_panel}{x}+$x_off,
                        $tree->{_empty_panel}{y}+$y_off
                    ]
                );
                $tree->{_empty_panel}{_paint} = 1;
            }
            $event->Skip;
        }
    );

}


sub GetSelectionsIds {
    my ( $self )=@_;


    return [
        grep { defined $_ }
        map {
            my $category = $self->GetPlData( $_ );
            $category != -1 ?
                $category->{id} :
                undef ;
        }
        ( $self->GetSelections ) 
    ];
}


sub AddCategory {
    my ( $self, $event ) = @_;

    $self->SelectDefaultParent;

    my $parent_category_id = $self->GetSelectionsIds->[0];
    my $parent_item = $self->GetSelection;

    my $dialog = Wx::TextEntryDialog->new( 
        $self, 
        wxTheApp->branding->{'Category name'}, 
        wxTheApp->branding->{'Add new category'},
        wxTheApp->branding->{'New category'}, 
    );

    if( $dialog->ShowModal != wxID_CANCEL ) {
        my $name = $dialog->GetValue;
        my ( $success, $status_msg, $content ) = wxTheApp->pwg->AddCategories( $name, $parent_category_id);

        if($success){
            $self->_append_category($parent_item, $name, $content->{result}{id});
            # direct, without test on pwg_categories
            # because of lazy refresh to avoid re-populating the whole tree
            $self->ShowHideEmptyCategoriesMsg;
            $self->frame_callback->() if 'CODE' eq ref $self->frame_callback;
        }
    }

    $dialog->Destroy;
}


sub SelectDefaultParent {
    my ( $self ) = @_;

    if(!scalar @{$self->GetSelectionsIds}){
        $self->SelectItem($self->GetRootItem);
    }
}

sub ShowHideEmptyCategoriesMsg {
    my ( $self ) = @_;

    $self->GetCount > 1 ?
        $self->HideEmptyMsg :
        $self->ShowEmptyMsg;
}


sub _append_category {
    my ( $self, $parent_id, $name, $id ) = @_;

    $self->SelectItem(
        $self->AppendItem(
            $parent_id, 
            $name, 
            1, 
            -1, 
            Wx::TreeItemData->new( { id => $id } )
        )
    );
}

1;
