/* Network-Integrated Multimedia Middleware (NMM)
 * http://www.motama.com/nmm.html
 *  
 * Copyright (C) 2006-2007
 * Motama GmbH, Saarbruecken, Germany
 * http://www.motama.com
 *  
 * This file is part of NMM. 
 * 
 * NMM is free software; you can redistribute it and/or modify it    
 * under the terms of the GNU General Public License as published by 
 * the Free Software Foundation; only version 2 of the License.      
 * 
 * NMM is distributed in the hope that it will be useful, but WITHOUT 
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 
 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 
 * License for more details.  
 * 
 * You should have received a copy of the GNU General Public License 
 * along with NMM; if not, write to the Free Software Foundation,    
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 */

#ifndef PROGRAMDESCRIPTION_HPP
#define PROGRAMDESCRIPTION_HPP PROGRAMDESCRIPTION_HPP

#include "nmm/nmm_prefix.hpp"

#include <iostream>
#include <list>
#include <string>

#include "nmm/comm/serialize/SerializedValue.hpp"
#include "nmm/comm/serialize/TValue.hpp"

#include "ChannelDescription.hpp"
#include "nmm/utils/time/LocalTime.hpp"

namespace NMM{

  /** \class ProgramDescription
   * This class represents a Programmeinformation for TVGuide. 
   */


  class ProgramDescription : public SerializedValue{

  public:
    enum timeLocale_t {GMT=0, LOCAL};

  private:
    NMM::TValue<LocalTime> startTime;
    NMM::TValue<LocalTime> endTime;
    
    NMM::TValue<ChannelDescription> channel;
    
    NMM::TValue<nmm_uint32> duration; //in minutes

    NMM::TValue<list<string> > title;
    NMM::TValue<string> desc;
    NMM::TValue<list<string> >category;

    NMM::TValue<nmm_uint32> sourcePriority;

    NMM::TValue<nmm_bool> startTimeEmpty;
    NMM::TValue<nmm_bool> endTimeEmpty;    

  public:
    ProgramDescription();
    ProgramDescription(unsigned int source);
    ProgramDescription (const ProgramDescription&);
    ~ProgramDescription();

    /**
     *Test, if the ProgramDescirption is empty.
     *@return true if it is empty
     *@return false otherwise
     */
    bool empty();

    /**
     *Set the start-time of the program
     *@param string starttime
     */
    void setStartTime(string st);
    /**
     *Set the start-time of the program
     *@param LocalTime starttime
     */
    void setStartTime(const LocalTime &st);
    /**
     *Get the start-time of the program
     *@resturn LocalTime starttime
     */
    LocalTime getStartTime(timeLocale_t l = LOCAL) const;
    bool getStartTimeEmpty() const { return startTimeEmpty.getRValue();}

    /**
     *Set the end-time of the program
     *@param string endtime
     */
    void setEndTime(string et);
    /**
     *Set the end-time of the program
     *@param LocalTime endtime
     */
    void setEndTime(const LocalTime &et);
    /**
     *Get the end-time of the program
     *@resturn LocalTime endtime
     */
    LocalTime getEndTime(timeLocale_t l = LOCAL) const;
    bool getEndTimeEmpty() const {return endTimeEmpty.getRValue();}

    /**
     *Set the ChannelID 
     *@param channel-ID
     */
    void setChannelID(string id);
    /**
     *Get the ChannelID 
     *@return string  channel-ID
     */
    string getChannelID() const;

    /**
     *Set the ChannelDescription 
     *@param channel-description
     */
    void setChannelDescription(ChannelDescription cd);
    /**
     *Get the ChannelDescription 
     *@return ChannelDescription
     */
    ChannelDescription getChannelDescription() const;

    /**
     *Set the Duration of the program 
     *@param duration
     */
    void setDuration(unsigned int d);
    /**
     *Get the duration 
     *@return unsigned int duration
     */
    unsigned int getDuration() const;

    /**
     *Sets a list of titles for this program
     *@param list of titles
     */
    void setTitles(list<string> titles);
    /**
     *Add a single title to the titles-list
     *@param title
     */
    void addTitle(string t);
    /**
     *Gets the titles of this program
     *@return list<string> titles
     */
    list<string> getTitles() const;

    /**
     *Set the description of this program
     *@param description
     */
    void setDescription(string d);
    /**
     *Get the description of this program
     *@return description
     */
    string getDescription() const;

    /**
     *Adds a category for this program
     *@param category
     */
    void addCategory(string c);
    /**
     *Get the list of categories set for this program
     *@return list<string> categories
     */
    list<string> getCategory() const;

    /**
     *returns the SourceType specified on creation
     *@return string source-type
     */
    unsigned int getSourcePriority() const { return sourcePriority.getRValue();}

    /**
     *sets the SourceType
     *@param source-type
     */
    void setSourcePriority(unsigned int t) {sourcePriority = t;}

    //Interface SerialzedValue
    ProgramDescription* copy();

    bool operator<(const ProgramDescription &pd) const;
    bool operator==(const ProgramDescription &pd) const;
    
  private:
    void registerValues();
    LocalTime stringToLocalTime(string s);
  };

  OValueStream& operator<<(OValueStream& os, const list<ProgramDescription>& pd);
  IValueStream& operator>>(IValueStream& is, list<ProgramDescription>& pd);




  class ProgramDescriptionList : public SerializedValue{
  private:
    NMM::TValue<list<ProgramDescription> > internal_list;

  public:
    ProgramDescriptionList() : SerializedValue("ProgramDescriptionList", "NMM"){registerAttributes();}
    ProgramDescriptionList(const ProgramDescriptionList &pl): SerializedValue("ProgramDescriptionList", "NMM"){*this=pl; registerAttributes();}
    ProgramDescriptionList(list<ProgramDescription> l): SerializedValue("ProgramDescriptionList", "NMM"){internal_list = l;registerAttributes();}
  private:
    void registerAttributes(){insertArgument(&internal_list);}

  public:
    list<ProgramDescription> getList() const {return internal_list.getRValue();}
    unsigned int size() const {return internal_list.getRValue().size();}
    void pus_back(ProgramDescription pd){internal_list.getRValue().push_back(pd);}
    ProgramDescription back() const {return internal_list.getRValue().back();}
    void pop_back() {internal_list.getRValue().pop_back();}
  };

  OValueStream& operator<<(OValueStream& os, const list<ProgramDescriptionList>& pl);
  IValueStream& operator>>(IValueStream& is, list<ProgramDescriptionList>&pl);





}
#include "nmm/nmm_suffix.hpp"

#endif
