/*
 * statusandquestion: A plugin for the Video Disk Recorder
 *
 * See the README file for copyright information and how to reach the author.
 *
 * $Id: messages.c 0.1 2004/07/11 14:12:20 hflor Exp $
 */

#include <stdlib.h>
#include <unistd.h>
#include "messages.h"
#include "statusandquestion.h"
#include "i18n.h"
#include "vdrtools.h"
#include <vdr/keys.h>

const char *MessageTypName(eMessageTyp MessageTyp)
{
  static const char *sMessageTyp[] = { "Typ0$status-message", "Typ1$info-message", "Typ2$warning-message", "Typ3$error-messsage", "Typ4$long text", "Typ5$vdr-status-message", "Typ6$parameter", "Typ7$set timeout", "Typ8$unknow typ" };
  return tr(sMessageTyp[MessageTyp < MessageTyp_min || MessageTyp > MessageTyp_none ? MessageTyp_none : MessageTyp]);
}

const char *MessageTypNameShort(eMessageTyp MessageTyp)
{
  static const char *sMessageTyp[] = { "Typ0$S", "Typ1$I", "Typ2$W", "Typ3$E", "Typ4$L", "Typ5$V", "Typ6$P", "Typ7$T", "Typ8$U" };
  return tr(sMessageTyp[MessageTyp < MessageTyp_min || MessageTyp > MessageTyp_none ? MessageTyp_none : MessageTyp]);
}

// -- cMessageData -----------------------------------------------------------------

cMessageData::cMessageData(eMessageTyp MessageTyp)
{
#ifdef SAQ_Debug
  dsyslog("%s: cMessageData::cMessageData [%s]", plugin_name, MessageTypName(MessageTyp));
#endif
  messagetyp = MessageTyp;
  text = NULL;
  textorg = NULL;
  timeout = 0;
  id = ++nextid;
  if (nextid > 9999)
    nextid = 0;
  for (int pos = MenuTyp_Title; pos <= MenuTyp_Blue; pos++)
    menu[pos] = NULL;
  receivetime = time(NULL);
  key = k_Setup; // key is not set
  responsetime = 0;
  usecount = 0;
}

cMessageData::~cMessageData(void)
{
#ifdef SAQ_Debug
  dsyslog("%s: cMessageData::~cMessageData %s [%s] %d", plugin_name, MessageTypName(messagetyp), text, usecount);
#endif
  if (text)
    free(text);
  for (int pos = MenuTyp_Title; pos <= MenuTyp_Blue; pos++)
  if (menu[pos])
    free(menu[pos]);
}

void cMessageData::SetTimeout(int Timeout)
{
#ifdef SAQ_Debug
  dsyslog("%s: cMessageData::SetTimeout [%d]", plugin_name, Timeout);
#endif
  timeout = Timeout;
}

void cMessageData::SetText(const char *Text)
{
#ifdef SAQ_Debug
  dsyslog("%s: cMessageData::SetText [%s]", plugin_name, Text);
#endif
  if (text)
    free(text);
  if (textorg)
    free(textorg);
  text = Text ? strdup(Text) : NULL;
#if VDRVERSNUM >= 10307
  bool ml = messagetyp == MessageTyp_Text;
#else
  bool ml = true; // allow multiline-text in vdr 1.2.6
#endif
  if (text && ml)
  {
    strreplace(text, '|', '\n');
    while (*text == '\n')
      strcpy(text, text + 1);
    while (*(text + strlen(text) - 1) == '\n')
      *(text + strlen(text) - 1) = 0;
  }
  textorg = text && strlen(text) ? strdup(text) : NULL;
  if (textorg)
  {
    strreplace(textorg, '\n', '|');
    if (ml)
    {
      if (*text == '@')
        *text = '\n';
      if (*(text + strlen(text) - 1) == '@')
        *(text + strlen(text) - 1) = '\n';
    }
  }
}

void cMessageData::SetMenu(eMenuTyp Choise, const char *Text)
{
#ifdef SAQ_Debug
  dsyslog("%s: cMessageData::SetMenu [%d - %s]", plugin_name, Choise, Text);
#endif
  if (Choise >= MenuTyp_Title && Choise <= MenuTyp_Blue)
  {
    if (menu[Choise])
      free(menu[Choise]);
    menu[Choise] = Text ? strdup(Text) : NULL;
  }
}

void cMessageData::SetKey(eKeys Key)
{
#ifdef SAQ_Debug
  dsyslog("%s: cMessageData::SetKey [%d (%s)]", plugin_name, Key, KeyName(Key));
#endif
  key = Key;
  responsetime = time(NULL);
}

// -- cMessage ----------------------------------------------------------------

cMessage::cMessage(cMessageData *MessageData)
{
  messagedata = MessageData;
  messagedata->IncUseCount();
}

cMessage::~cMessage(void)
{
  if (messagedata->DecUseCount())
    delete messagedata;
}

// -- cMessages ----------------------------------------------------------------

bool cMessages::SetLock(bool Lock, bool Wait)
{
  if (Lock)
  {
    if (lock && !Wait)
      return false;
    for (int i = 0; i < 30; i++)
      if (lock)
        usleep(25000);
      else
        break;
    if (lock)
      return false;
    lock = getpid();
    usleep(10);
    if (lock != getpid())
      return false;
  } else
    lock = 0;
  return true;
}

cMessage *cMessages::SearchMessage(cMessageData *MessageData)
{
#ifdef SAQ_Debug
  dsyslog("%s: cMessages::SearchMessage ID=%d", plugin_name, MessageData ? MessageData->ID() : -1);
#endif

  if (MessageData)
  {
    cMessage *message = First();
    while (message)
    {
      if (message->MessageData() == MessageData)
        return message;
      message = Next(message);
    }
  }
  return NULL;
}

cMessages Messages;
cMessages Responses;
cMessages History;
