/***************************************************************************
 *   Copyright (C) 2005 by S�astien Laot                                 *
 *   slaout@linux62.org                                                    *
 *                                                                         *
 *   This program 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; either version 2 of the License, or     *
 *   (at your option) any later version.                                   *
 *                                                                         *
 *   This program 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 this program; if not, write to the                         *
 *   Free Software Foundation, Inc.,                                       *
 *   51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.             *
 ***************************************************************************/

#ifndef TAG_H
#define TAG_H

#include <tqstring.h>
#include <tqcolor.h>
#include <tqfont.h>
#include <tqvaluelist.h>

#include <tdeaction.h>
#include <tdeshortcut.h>

class TQPainter;

class Tag;

/**
  * @author S�astien Laot
  */
class State
{
  public:
	/// LIST OF STATES:
	typedef TQValueList<State*> List;

  public:
	/// CONSTRUCTOR AND DESTRUCTOR:
	State(const TQString &id = TQString(), Tag *tag = 0);
	~State();
	/// SET PROPERTIES:
	void setId(const TQString &id)                { m_id              = id;        }
	void setName(const TQString &name)            { m_name            = name;      }
	void setEmblem(const TQString &emblem)        { m_emblem          = emblem;    }
	void setBold(bool bold)                      { m_bold            = bold;      }
	void setItalic(bool italic)                  { m_italic          = italic;    }
	void setUnderline(bool underline)            { m_underline       = underline; }
	void setStrikeOut(bool strikeOut)            { m_strikeOut       = strikeOut; }
	void setTextColor(const TQColor &color)       { m_textColor       = color;     }
	void setFontName(const TQString &font)        { m_fontName        = font;      }
	void setFontSize(int size)                   { m_fontSize        = size;      }
	void setBackgroundColor(const TQColor &color) { m_backgroundColor = color;     }
	void setTextEquivalent(const TQString &text)  { m_textEquivalent  = text;      }
	void setOnAllTextLines(bool yes)             { m_onAllTextLines  = yes;       }
	void setParentTag(Tag *tag)                  { m_parentTag       = tag;       }
	/// GET PROPERTIES:
	TQString id()              const { return m_id;              }
	TQString name()            const { return m_name;            }
	TQString emblem()          const { return m_emblem;          }
	bool    bold()            const { return m_bold;            }
	bool    italic()          const { return m_italic;          }
	bool    underline()       const { return m_underline;       }
	bool    strikeOut()       const { return m_strikeOut;       }
	TQColor  textColor()       const { return m_textColor;       }
	TQString fontName()        const { return m_fontName;        }
	int     fontSize()        const { return m_fontSize;        }
	TQColor  backgroundColor() const { return m_backgroundColor; }
	TQString textEquivalent()  const { return m_textEquivalent;  }
	bool    onAllTextLines()  const { return m_onAllTextLines;  }
	Tag*    parentTag()       const { return m_parentTag;       }
	/// HELPING FUNCTIONS:
	State *nextState(bool cycle = true);
	TQString fullName();
	TQFont font(TQFont base);
	TQString toCSS(const TQString &gradientFolderPath, const TQString &gradientFolderName, const TQFont &baseFont);
	static void merge(const List &states, State *result, int *emblemsCount, bool *haveInvisibleTags, const TQColor &backgroundColor);
	void copyTo(State *other);
  private:
	/// PROPERTIES:
	TQString  m_id;
	TQString  m_name;
	TQString  m_emblem;
	bool     m_bold;
	bool     m_italic;
	bool     m_underline;
	bool     m_strikeOut;
	TQColor   m_textColor;
	TQString  m_fontName;
	int      m_fontSize;
	TQColor   m_backgroundColor;
	TQString  m_textEquivalent;
	bool     m_onAllTextLines;
	Tag     *m_parentTag;
};

/** A Tag is a category of Notes.
  * A Note can have 0, 1 or more Tags.
  * A Tag can have a unique State or several States.
  * @author S�astien Laot
  */
class Tag
{
  public:
	/// LIST OF ALL TAGS IN THE APPLICATION:
	typedef TQValueList<Tag*> List;
	static Tag::List all;
	static State* stateForId(const TQString &id);
	static Tag* tagForTDEAction(TDEAction *action);
	static Tag* tagSimilarTo(Tag *tagToTest);
	static TQMap<TQString, TQString> loadTags(const TQString &path = TQString()/*, bool merge = false*/); /// << Load the tags contained in the XML file @p path or those in the application settings if @p path isEmpty(). If @p merge is true and a tag with the id of a tag that should be loaded already exist, the tag will get a new id. Otherwise, the tag will be dismissed.
	static void saveTags();
	static void saveTagsTo(TQValueList<Tag*> &list, const TQString &fullPath);
	static void createDefaultTagsSet(const TQString &file);
	static long getNextStateUid();
  private:
	static long nextStateUid;

  public:
	/// CONSTRUCTOR AND DESTRUCTOR:
	Tag(/*State *firstState, const TQString &name, bool inheritedBySiblings*/);
	~Tag();
	/// SET PROPERTIES:
	void setName(const TQString &name);
	void setShortcut(const TDEShortcut &shortcut) { m_action->setShortcut(shortcut);                   }
	void setInheritedBySiblings(bool inherited) { m_inheritedBySiblings = inherited;                 }
	void appendState(State *state)              { m_states.append(state); state->setParentTag(this); }
	void removeState(State *state)              { m_states.remove(state); state->setParentTag(0);    }
	/// GET PROPERTIES:
	TQString      name()                const { return m_name;                 }
	TDEShortcut    shortcut()            const { return m_action->shortcut();   }
	bool         inheritedBySiblings() const { return m_inheritedBySiblings;  }
	State::List& states()              const { return (State::List&)m_states; }
	int          countStates()         const { return m_states.count();       }
	void copyTo(Tag *other);
  private:
	/// PROPERTIES:
	TQString      m_name;
	TDEAction     *m_action;
	bool         m_inheritedBySiblings;
	State::List  m_states;
};

#include <tqiconset.h>
#include <tqmenudata.h>
#include <tqstring.h>

class TQPainter;

/** A menu item to indent icon and text (to keep place for a checkbox or a radiobutton on left).
  * You should not set any icon when adding this entry to the menu.
  * Instead, the constructor take the icon and the item take care to draw it itself.
  * Better suited to be used with StateMenuItem (or TagMenuItem).
  * @author S�astien Laot
  */
class IndentedMenuItem : public TQCustomMenuItem
{
  public:
	IndentedMenuItem(const TQString &text, const TQString &icon = "", const TQString &shortcut = "");
	~IndentedMenuItem();
	void paint(TQPainter *painter, const TQColorGroup &cg, bool active, bool enabled, int x, int y, int w, int h);
	TQSize sizeHint();
	bool fullSpan() { return true; }
  private:
	TQString  m_text;
	TQString  m_icon;
	TQString  m_shortcut;
};

/** A menu item representing a State or a Tag.
  * @author S�astien Laot
  */
class StateMenuItem : public TQCustomMenuItem
{
  public:
	StateMenuItem(State *state, const TQString &shortcut, bool withTagName = false);
	~StateMenuItem();
	void paint(TQPainter *painter, const TQColorGroup &cg, bool active, bool enabled, int x, int y, int w, int h);
	TQSize sizeHint();
	bool fullSpan() { return true; }
  private:
	State   *m_state;
	TQString  m_name;
	TQString  m_shortcut;
  public:
	static TQIconSet checkBoxIconSet(bool checked, TQColorGroup cg);
	static TQIconSet radioButtonIconSet(bool checked, TQColorGroup cg);
	static int iconMargin() { return 5; }
};

#endif // TAG_H
