/*
 * autotimeredit: A plugin for the Video Disk Recorder
 *
 * See the README file for copyright information and how to reach the author.
 *
 * $Id: menusetup.c 1.7 2005/10/19 23:22:17 hflor Exp $
 */

#include "autotimeredit.h"
#include "menuautotimer.h"
#include "ddictionary.h"
#include "menudictionary.h"
#include "menusetup.h"
#include "vdrtools.h"
#include "i18n.h"
#if VDRVERSNUM < 10305
  #include "menueditbit.h"
#endif
#if VDRVERSNUM >= 10307
  #include <vdr/font.h>
#endif

// --- cMenuSetupAutoTimer -------------------------------------------------------

cMenuSetupAutoTimer::cMenuSetupAutoTimer(void)
{
#ifdef ATE_Debug2
  dsyslog("%s: cMenuSetupAutoTimer::cMenuSetupAutoTimer", plugin_name);
#endif
  show_setup = false;
  show_dictionary = false;
  display_int = true;
  store = false;
#if VDRVERSNUM >= 10307
  editwidth = DisplayMenu()->EditableWidth() + 12 * 33; // tab(0) for Setup (skins.c)
#endif

  #define StoreValue(T) T.o = T.u
  #define StoreValueChar(T) strcpy(T.o, T.u)

  // var pos7
  StoreValueChar (autotimerfile);
  StoreValue     (commandline_preference);
  StoreValueChar (mainmenu_name);
  StoreValue     (mainmenu_visible);
  StoreValue     (num_entrys);
  StoreValue     (question);
  StoreValue     (searchlength);
  StoreValue     (show_channel);
  StoreValue     (show_channelname);
  StoreValue     (show_flags);
  StoreValue     (show_startstop);
  StoreValue     (update_b_e);
  StoreValue     (updatemethod);
  StoreValue     (updatetimerecords);
  StoreValue     (use_defaultdictionary);
  StoreValue     (use_except_repeat);
  StoreValue     (use_weekdays);
  StoreValueChar (vdradminconfig);
  StoreValueChar (vdradminupdate);
  StoreValue     (verbose);

  #undef StoreValue
  #undef StoreValueChar

  Set();
}

cMenuSetupAutoTimer::~cMenuSetupAutoTimer(void)
{
#ifdef ATE_Debug2
  dsyslog("%s: cMenuSetupAutoTimer::~cMenuSetupAutoTimer store=%s", plugin_name, store ? "true" : "false");
#endif
  if (!display_int) {
    updatetimerecords.u--;
    display_int = true;
  }
  if (!store) {

    #define RestoreValue(T) T.u = T.o
    #define RestoreValueChar(T) strcpy(T.u, T.o)

    // var pos8
    RestoreValueChar (autotimerfile);
    RestoreValue     (commandline_preference);
    RestoreValueChar (mainmenu_name);
    RestoreValue     (mainmenu_visible);
    RestoreValue     (num_entrys);
    RestoreValue     (question);
    RestoreValue     (searchlength);
    RestoreValue     (show_channel);
    RestoreValue     (show_channelname);
    RestoreValue     (show_flags);
    RestoreValue     (show_startstop);
    RestoreValue     (update_b_e);
    RestoreValue     (updatemethod);
    RestoreValue     (updatetimerecords);
    RestoreValue     (use_defaultdictionary);
    RestoreValue     (use_except_repeat);
    RestoreValue     (use_weekdays);
    RestoreValueChar (vdradminconfig);
    RestoreValueChar (vdradminupdate);
    RestoreValue     (verbose);

    #undef RestoreValue
    #undef RestoreValueChar
  }
}

void cMenuSetupAutoTimer::Store(void)
{
#ifdef ATE_Debug2
  dsyslog("%s: cMenuSetupAutoTimer::Store", plugin_name);
#endif

  if (!display_int) {
    updatetimerecords.u--;
    display_int = true;
  }

  #define SaveValue(T, N) if (T.u != T.o) SetupStore(N, T.u);
  #define SaveValueChar(T, N) if (strcmp(T.u, T.o)) SetupStore(N, T.u);

  if (use_weekdays.u) use_except_repeat.u = true; 
  // var pos9
  SaveValueChar (autotimerfile,          "autotimerfile");
  SaveValue     (commandline_preference, "commandline");
  SaveValueChar (mainmenu_name,          "name");
  SaveValue     (mainmenu_visible,       "visible");
  SaveValue     (num_entrys,             "entrys");
  SaveValue     (question,               "question");
  SaveValue     (searchlength,           "searchlength");
  SaveValue     (show_channel,           "channel");
  SaveValue     (show_channelname,       "channelname");
  SaveValue     (show_flags,             "flags");
  SaveValue     (show_startstop,         "startstop");
  SaveValue     (update_b_e,             "updatelines");
  SaveValue     (updatemethod,           "updatemethod");
  SaveValue     (updatetimerecords,      "updatetime");
  SaveValue     (use_defaultdictionary,  "defaultdictionary");
  SaveValue     (use_except_repeat,      "except_repeat");
  SaveValue     (use_weekdays,           "weekdays");
  SaveValueChar (vdradminconfig,         "vdradminconfig");
  SaveValueChar (vdradminupdate,         "vdradminupdate");
  SaveValue     (verbose,                "verbose");

  #undef SaveValue
  #undef SaveValueChar

  SetupStore    ("countdictionary",      SetupDefaultDictionarys.Count());
  int i = 0;
  char *name = NULL;
  char *value = NULL;
  cDefaultDictionary *DD = SetupDefaultDictionarys.First();
  while (DD) {
    asprintf(&name, "dictionary%03d", ++i);
    asprintf(&value, "%s%s", DD->Blacklist() ? DD->Includesub() ? "~~" : "~" : "", DD->Dictionary());
    SetupStore(name, value);
    free(name);
    free(value);
    DD = SetupDefaultDictionarys.Next(DD);
  }
  store = true;
}

void cMenuSetupAutoTimer::Set(void)
{
#ifdef ATE_Debug2
  dsyslog("%s: cMenuSetupAutoTimer::Set Current=%d", plugin_name, Current());
#endif
  int current = Current();
#if VDRVERSNUM >= 10307
  cOsdItem *item;
#endif
  Clear();
  fileitempos1 = -1;
  fileitempos2 = -1;
  fileitempos3 = -1;

  #define DisplayLine(T) !T.h && (!commandline_preference.u || !T.c)

  Add(new cOsdItem         (tr("Setup$Edit Autotimer now"),                              osUser1));
  if (DisplayLine(commandline_preference))
    Add(new cMenuEditBoolItem(tr("Setup$Preferr Command Line Parameter"),                &commandline_preference.u));
  if (DisplayLine(autotimerfile)) {
    fileitempos1 = Count();
    Add(new cMenuEditStrItem (tr("Setup$Path for vdradmind.at"),                         autotimerfile.u, sizeof(autotimerfile.u), FileNameCharsAllowed));
  }
  if (DisplayLine(searchlength))
    Add(new cMenuEditIntItem (tr("Setup$minimum search text length"),                    &searchlength.u, 0, 99));
  if (DisplayLine(use_except_repeat))
    Add(new cMenuEditBoolItem(tr("Setup$Except repeat Feature (bigpatch 0.9)"),          &use_except_repeat.u));
  if (DisplayLine(use_weekdays))
    Add(new cMenuEditBoolItem(tr("Setup$Autotimer with weekdays (am 3.4.1)"),            &use_weekdays.u));
  if (DisplayLine(mainmenu_visible))
    Add(new cMenuEditBoolItem(tr("Setup$Visible in Mainmenu"),                           &mainmenu_visible.u));
  if (DisplayLine(mainmenu_name) && mainmenu_visible.u)
    Add(new cMenuEditStrItem (tr("Setup$  Name for Mainmenu"),                           mainmenu_name.u, sizeof(mainmenu_name.u), tr(FileNameChars)));
  if (DisplayLine(verbose))
    Add(new cMenuEditBoolItem(tr("Setup$Verbose Log Mode"),                              &verbose.u));

  if (!commandline_preference.u || !show_flags.c || !show_channel.c || !show_channelname.c || !show_startstop.c)
    Add(new cMenuEditBoolItem(tr("Setup$Setup List Format"),                             &show_setup));
  if (show_setup) {
    if (DisplayLine(show_flags))
      Add(new cMenuEditBoolItem(tr("Setup$  Show Flags"),                                &show_flags.u));
    if (DisplayLine(show_channel))
      Add(new cMenuEditBoolItem(tr("Setup$  Show Channel"),                              &show_channel.u));
    if (DisplayLine(show_channelname) && show_channel.u)
      Add(new cMenuEditBoolItem(tr("Setup$    Use Channelname"),                         &show_channelname.u));
    if (DisplayLine(show_startstop))
      Add(new cMenuEditStraItem(tr("Setup$  Show start/stop Time"),                      &show_startstop.u, 4, StartStopTime));
  }
  bool display_defaultdictionary = DisplayLine(use_defaultdictionary);
  if (display_defaultdictionary)
    Add(new cMenuEditBoolItem(tr("Setup$Configure default dictionary"),                  &show_dictionary));
  else if (DisplayLine(updatetimerecords) && (use_defaultdictionary.u & Source_Records)) {
    show_dictionary = true;
#if VDRVERSNUM >= 10307
    item = new cOsdItem(tr("Setup$*Default dictionary from records"),                    osUser9);
    item->SetSelectable(false);
    Add(item);
#else
    Add(new cOsdItem(tr("Setup$*Default dictionary from records"),                       osUser9));
#endif
  }
  if (show_dictionary) {
    if (display_defaultdictionary) {
#if VDRVERSNUM >= 10307
      item = new cOsdItem(tr("Setup$  *Sources for default dictionary ..."),             osUser9);
      item->SetSelectable(false);
      Add(item);
#else
      Add(new cOsdItem(tr("Setup$  *Sources for default dictionary ..."),                osUser9));
#endif
#if VDRVERSNUM >= 10338
      Add(new cMenuEditBitItem(tr("Setup$  ... Records"),                                (uint *)&use_defaultdictionary.u, Source_Records));
#else
      Add(new cMenuEditBitItem(tr("Setup$  ... Records"),                                &use_defaultdictionary.u, Source_Records));
#endif
    }
    if (DisplayLine(updatetimerecords) && (use_defaultdictionary.u & Source_Records)) {
      if (updatetimerecords.u < (display_int ? 1 : 2)) {
        if (display_int) {
          updatetimerecords.u++;
          display_int = false;
        }
        Add(new cMenuEditStraItem(tr(display_defaultdictionary ? "Setup$    Time for update records" : "Setup$  Time for update records"), &updatetimerecords.u, 3, RecordsUpdateTime));
      } else {
        if (!display_int) {
          updatetimerecords.u--;
          display_int = true;
        }
        Add(new cMenuEditIntItem (tr(display_defaultdictionary ? "Setup$    Time for update records (hour)" : "Setup$  Time for update records (hour)"), &updatetimerecords.u, 0, 99));
      }
    }
    if (display_defaultdictionary) {
#if VDRVERSNUM >= 10338
      Add(new cMenuEditBitItem(tr("Setup$  ... Autotimers"),                             (uint *)&use_defaultdictionary.u, Source_AutoTimers));
      Add(new cMenuEditBitItem(tr("Setup$  ... Timers"),                                 (uint *)&use_defaultdictionary.u, Source_Timers));
      Add(new cMenuEditBitItem(tr("Setup$  ... Commandline"),                            (uint *)&use_defaultdictionary.u, Source_Commandline));
      Add(new cMenuEditBitItem(tr("Setup$  ... Setup list"),                             (uint *)&use_defaultdictionary.u, Source_Setup));
#else
      Add(new cMenuEditBitItem(tr("Setup$  ... Autotimers"),                             &use_defaultdictionary.u, Source_AutoTimers));
      Add(new cMenuEditBitItem(tr("Setup$  ... Timers"),                                 &use_defaultdictionary.u, Source_Timers));
      Add(new cMenuEditBitItem(tr("Setup$  ... Commandline"),                            &use_defaultdictionary.u, Source_Commandline));
      Add(new cMenuEditBitItem(tr("Setup$  ... Setup list"),                             &use_defaultdictionary.u, Source_Setup));
#endif
    }
  }
  if (DisplayLine(updatemethod))
    Add(new cMenuEditStraItem(tr("Setup$Method for manual search update"),               &updatemethod.u, 5, UpdateMethod));
  if (DisplayLine(vdradminconfig) && updatemethod.u == 0x1) {
    fileitempos2 = Count();
    Add(new cMenuEditStrItem (tr("Setup$  Path for config file"),                        vdradminconfig.u, sizeof(vdradminconfig.u), FileNameCharsAllowed));
  }
  if (DisplayLine(vdradminupdate) && updatemethod.u == 0x2) {
    fileitempos3 = Count();
    Add(new cMenuEditStrItem (tr("Setup$  Path for update script"),                      vdradminupdate.u, sizeof(vdradminupdate.u), FileNameCharsAllowed));
  }
  if (DisplayLine(update_b_e) && updatemethod.u != 0)
    Add(new cMenuEditStraItem(tr("Setup$  Updateline position"),                         &update_b_e.u, 4, UpdateLine));
  if (DisplayLine(num_entrys) && updatemethod.u != 0 && update_b_e.u == 0x3)
    Add(new cMenuEditIntItem (tr("Setup$    Display bottom update ex lines"),            &num_entrys.u, 1, 200));
  if (DisplayLine(question) && updatemethod.u != 0)
    Add(new cMenuEditStraItem(tr("Setup$  After change force new search"),               &question.u, 3, UpdateQuestion));
  if (updatemethod.u != 0)
    Add(new cOsdItem       (tr("Setup$Now force search update"),                         osUser2));
  if (!use_defaultdictionary.h && (use_defaultdictionary.u & Source_Setup))
    Add(new cOsdItem(tr("Setup$Modify dictionarys list"),                                osUser3));

  #undef DisplayLine

#if VDRVERSNUM >= 10307
  item = new cOsdItem(" ", osUser9);
  item->SetSelectable(false);
  Add(item);
  cTextWrapper *textwrapper = new cTextWrapper(tr("Setup$For this plugin is vdradmind or xxv requiered!\nIn the config of vdradmind must the autotimer-function be enabled."), cFont::GetFont(fontOsd), editwidth);
  for (int i = 0; i < textwrapper->Lines(); i++) {
    item = new cOsdItem(textwrapper->GetLine(i), osUser9);
    item->SetSelectable(false);
    Add(item);
  }
  delete textwrapper;
  Add(new cOsdItem(" "), osUser9);
#else
  Add(new cOsdItem(" ", osUser9));
  char *comment = strdup(tr("Setup$For this plugin is vdradmind or xxv requiered!\nIn the config of vdradmind must the autotimer-function be enabled."));
  char *pos = comment;
  char *pos_next;
  char *pos_last;
  char text[MAXOSDWIDTH + 1];
  int textlen;

  while (*pos) {
    pos_next = strchr(pos, '\n');
    if (!pos_next)
      pos_next = pos + strlen(pos);
    textlen = pos_next - pos;
    if (textlen <= Setup.OSDwidth) {
      strn0cpy(text, pos, textlen + 1);
    } else {
      strn0cpy(text, pos, Setup.OSDwidth + 1);
      pos_last = strrchr(text, ' ');
      if (!pos_last)
        pos_last = text + Setup.OSDwidth + 1;
      *pos_last = 0;
      textlen = pos_last - text;
    }
    Add(new cOsdItem(text));
    pos += textlen;
    if (*pos) pos++;
  }
  free(comment);
#endif
#ifdef ATE_Debug1
  dsyslog("%s: Count=%d", plugin_name, Count());
#endif
  SetCurrent(Get(current));
}

void cMenuSetupAutoTimer::Display(void)
{
#ifdef ATE_Debug2
  dsyslog("%s: cMenuSetupAutoTimer::Display updatemethod=%d", plugin_name, updatemethod.u);
#endif
  cMenuSetupPage::Display();
  if (updatemethod.u == 0x3 && AutoTimers.GetUpdatePID() <= 0)
    SetStatus(tr("Error$vdradmind is not running on this machine"));
  else if (updatemethod.u == 0x4 && AutoTimers.GetUpdatePID() <= 0)
    SetStatus(tr("Error$xxv is not running on this machine"));
  else
    SetStatus(NULL);
}

eOSState cMenuSetupAutoTimer::ProcessKey(eKeys Key)
{
#ifdef ATE_Debug3
  bool noneKey = Key == kNone;
  if (!noneKey)
    dsyslog("%s: cMenuSetupAutoTimer::ProcessKey Key=%s", plugin_name, KeyName(Key));
#endif

#if VDRVERSNUM < 10307
  static char oldstatus[MAXOSDTEXTWIDTH];
  char status[MAXOSDTEXTWIDTH];
  tParamFile *filename;
  int pathlen;
#endif
  int m_commandline_preference = commandline_preference.u;
  int m_mainmenu_visible = mainmenu_visible.u;
  int m_show_setup = show_setup;
  int m_show_channel = show_channel.u;
  int m_show_dictionary = show_dictionary;

  int m_sel_Setup = use_defaultdictionary.u & Source_Setup;
  int m_sel_Records = use_defaultdictionary.u & Source_Records;
  int m_updatemethod = updatemethod.u;
  int m_update_b_e = update_b_e.u;

  eOSState state = cMenuSetupPage::ProcessKey(Key);

#ifdef ATE_Debug3
  if (!noneKey || (state != osUnknown && state != osContinue)) {
    dsyslog("%s: cMenuSetupAutoTimer::ProcessKey OSState=%s", plugin_name, OSStateName(state));
    noneKey = false;
  }
#endif

  if (m_commandline_preference != commandline_preference.u || m_mainmenu_visible != mainmenu_visible.u || m_show_setup != show_setup || m_show_channel != show_channel.u || m_show_dictionary != show_dictionary || m_sel_Records != (use_defaultdictionary.u & Source_Records) || show_dictionary && (use_defaultdictionary.u & Source_Records) && ((updatetimerecords.u < (display_int ? 1 : 2)) == display_int) || m_sel_Setup != (use_defaultdictionary.u & Source_Setup) || m_updatemethod != updatemethod.u || m_update_b_e != update_b_e.u) {
    Set();
    Display();
  }
#if VDRVERSNUM < 10307
  if (Current() == fileitempos1 || Current() == fileitempos2 || Current() == fileitempos3) {
    if (Current() == fileitempos1) filename = &autotimerfile;
      else if (Current() == fileitempos2) filename = &vdradminconfig;
        else filename = &vdradminupdate;
    pathlen = strlen(filename->u);
    if (pathlen > AKTOSDTEXTWIDTH - 10) {
      sprintf(status, "...%s", &filename->u[pathlen - AKTOSDTEXTWIDTH + 10]);
    } else
      strcpy(status, filename->u);
    if (oldstatus != status) {
      SetStatus(status);
      strcpy(oldstatus, status);
    }
  } else
    if (strlen(oldstatus)) {
      SetStatus(NULL);
      oldstatus[0] = 0;
    }
#endif

  switch (state) {
    case osBack:
    case osUnknown: if (Key == kOk) {
                      if (!AutoTimers.TestUpdate(true))
                        state = osContinue;
                      else if ((use_except_repeat.o && !use_except_repeat.u) || (use_weekdays.o && !use_weekdays.u))
                        if (Interface->Confirm(tr("Setup$Remove extensions from file?"))) {
                          if (!use_except_repeat.u) {
                            use_except_repeat.i = true;
                            use_weekdays.u = false;
                          }
                          if (!use_weekdays.u)
                            use_weekdays.i = true;
                        } else  
                          state = osContinue;
                    }
                    break;
    case osUser1:   state = AddSubMenu(new cMenuAutoTimers);
                    break;
    case osUser2:   if (AutoTimers.TestUpdate(true))
                      AutoTimers.RunUpdate();
                    state = osContinue;
                    break;
    case osUser3:   state = AddSubMenu(new cMenuDictionarys);
                    break;
    case osUser9:   state = osContinue;
                    break;
    default:        break;
  }

#ifdef ATE_Debug3
  if (!noneKey || (state != osUnknown && state != osContinue))
    dsyslog("%s: cMenuSetupAutoTimer::ProcessKey returned OSState=%s", plugin_name, OSStateName(state));
#endif
  return state;
}
