/* This file is part of cardwords
   (c) 1999 Tobias Peters
   see file COPYING for the copyright terms.
   
   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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
*/

// cardwords_gtk_cardcell.hh

#ifndef CARDWORDS_GTK_CARDCELL_HH
#define CARDWORDS_GTK_CARDCELL_HH

#ifndef WORD_FACTOR_MARKER
#define WORD_FACTOR_MARKER "W"
#endif
#ifndef LETTER_FACTOR_MARKER
#define LETTER_FACTOR_MARKER "L"
#endif

#include "cardwords_gtk_common_card_cell_styles.hh"
#include "cardwords_cardbase.hh"
#include <strstream.h>
#include "cardwords_gtk_cellattributetype.hh"
#include "config.hh"
#include <gtk--/eventbox.h>
#include <gtk--/box.h>

class CardWords_Gtk_CellAttribute : public Gtk::EventBox {
public:
  CardWords_Gtk_CellAttribute(const
                              CardWords_Gtk_Common_Card_Cell_Styles *
                              styles,

                              CardWords_Gtk_CellAttributeType type);
  virtual ~CardWords_Gtk_CellAttribute();

  CardWords_Gtk_CellAttributeType
  get_cell_attribute_type(void) const;

private:
  CardWords_Gtk_CellAttributeType cell_attribute_type;
};


class CardWords_Gtk_CellAttributeValue : public CardWords_Gtk_CellAttribute
{
public:
  CardWords_Gtk_CellAttributeValue(const
                                   CardWords_Gtk_Common_Card_Cell_Styles *
                                   styles,

                                   CardWords_Gtk_CellAttributeType type,
                                   int value);
  virtual ~CardWords_Gtk_CellAttributeValue();

  int
  get_value(void) const;

private:
  int value;
  Gtk::Label * label;
};

class CardWords_Gtk_CellAttributeDefault : public CardWords_Gtk_CellAttribute
{
public:
  CardWords_Gtk_CellAttributeDefault(const
                                     CardWords_Gtk_Common_Card_Cell_Styles *
                                     styles,

                                     CardWords_Gtk_CellAttributeType
                                     type = CAT_DEFAULT)
    : CardWords_Gtk_CellAttribute(styles, type)
    { assert(type == CAT_DEFAULT); };
};

class CardWords_Gtk_CellAttributeBlocked : public CardWords_Gtk_CellAttribute
{
public:
  CardWords_Gtk_CellAttributeBlocked(const
                                     CardWords_Gtk_Common_Card_Cell_Styles *
                                     styles,

                                     CardWords_Gtk_CellAttributeType
                                     type = CAT_BLOCKED)
    : CardWords_Gtk_CellAttribute(styles, type)
    { assert(type == CAT_BLOCKED); };
};

CardWords_Gtk_CellAttribute *
make_new_cell_attribute(const
                        CardWords_Gtk_Common_Card_Cell_Styles *
                        styles,

                        CardWords_Gtk_CellAttributeType type,
                        int value = 0);
                        
class CardWords_Gtk_EmptyCell : public Gtk::VBox {
public:
  CardWords_Gtk_EmptyCell (const
                           CardWords_Gtk_Common_Card_Cell_Styles *
                           styles,
                           int word_factor   = DEFAULT_WORD_FACTOR,
                           int letter_factor = DEFAULT_LETTER_FACTOR,
                           int cell_points   = DEFAULT_CELL_POINTS,
                           bool cell_blocked = false);
  ~CardWords_Gtk_EmptyCell ();

  int
  get_word_factor(void) const;
  int
  get_letter_factor(void) const;
  int
  get_cell_points(void) const;
  bool
  is_cell_blocked(void) const;

private:
  int word_factor;
  int letter_factor;
  int cell_points;
  bool cell_blocked;
  
  CardWords_Gtk_CellAttribute * attribute[2];
};

class CardWords_Gtk_CellCard : public Gtk::EventBox {
public:
  CardWords_Gtk_CellCard (const
                          CardWords_Gtk_Common_Card_Cell_Styles *
                          styles,
                          gchar face,
                          gint  pts,
                          bool  wild = false,
                          bool  s_recent = false,
                          bool  s_pre    = false);
  ~CardWords_Gtk_CellCard();

  gchar
  get_visible(void) const;

  int
  get_points(void) const;

  bool
  is_wildcard(void) const;
  bool
  is_recent(void) const;
  bool
  is_pre(void) const;
  
private:
  gchar visible[2];   // Face value or meaning
  gchar points[3]; // up to 2 digits for the points

  int int_points;

  bool  wildcard;
  bool  recent; // When the card was recently layed
  bool  pre;    // When the card is not yet layed
  
  Gtk::Label * c_label; // The label for face value or meaning;
  Gtk::Label * p_label; // The label for the points;

  Gtk::HBox  * hbox;
  Gtk::VBox  * points_box;
};

class CardWords_Gtk_CardCell : public Gtk::EventBox {
public:
  void
  activate(bool); // draw a light frame around the card cell if true.
  
  CardWords_Gtk_CardCell(const CardWords_Gtk_Common_Card_Cell_Styles * styles,
                         size_t coordinate,
                         int word_factor   = DEFAULT_WORD_FACTOR,
                         int letter_factor = DEFAULT_LETTER_FACTOR,
                         int cell_points   = DEFAULT_CELL_POINTS,
                         bool cell_blocked = false);


  void
  set_card (CardWords_Gtk_CellCard  * cellcard);
  void
  set_card (gchar face,
            gint  pts,
            bool  wild = false,
            bool  s_recent = false,
            bool  s_pre    = false);
  void
  set_card (const CardWords_CardBase *,
            bool  s_recent = false,
            bool  s_pre    = false);

  ~CardWords_Gtk_CardCell();

  int
  get_word_factor(void) const;
  int
  get_letter_factor(void) const;

  int
  get_cell_points(void) const;
  bool
  is_cell_blocked(void) const;
  
  const CardWords_Gtk_CellCard *
  get_cellcard(void) const;

  size_t
  get_coordinate(void) const;

  // Signal raised when the mouse pointer enters this card cell:
  SigC::Signal1<void, const CardWords_Gtk_CardCell *> enter_signal;
  // Signal raised when a click on this card cell has been performed:
  SigC::Signal1<void, const CardWords_Gtk_CardCell *> clicked_signal;
  
private:
  CardWords_Gtk_EmptyCell * ec;
  CardWords_Gtk_CellCard  * ct;

  size_t coordinate;
  
  Gtk::EventBox * inner_box;
  
  const CardWords_Gtk_Common_Card_Cell_Styles * styles;
  
  bool active;

  int send_enter_signal(GdkEventCrossing *);

  int button_pressed(GdkEventButton*);
  int button_released(GdkEventButton*);
  int pointer_leaves(GdkEventCrossing*);

  bool mouse_button_is_pressed;
};

#endif
