/**********************************************************************
 *
 *   FreeDoko a Doppelkopf-Game
 *
 *   Copyright (C) 2001-2006  by Diether Knof and Borg Enders
 *
 *   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 can find this license in the file 'gpl.txt'.
 *
 *   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
 *
 *  Contact:
 *    Diether Knof dknof@gmx.de
 *    Borg Enders  borg@borgsoft.de
 *
 *********************************************************************/

#include "constants.h"

#include "ui.wrap.h"

#include "../card/hand.h"

#ifdef USE_NETWORK
#include "../network/listener.h"
#include "../network/connection.h"
#endif

/**
 ** Constructor
 ** a ui of the type 'DUMMY' and no os
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
UI_Wrap::UI_Wrap() :
UI(UI_TYPE::WRAP),
  ui(UI::new_(UI_TYPE::DUMMY)),
os()
{
  return ;
} // UI_Wrap::UI_Wrap()

/**
 ** Destructor
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
UI_Wrap::~UI_Wrap()
{
  return ;
} // UI_Wrap::~UI_Wrap()

/**
 ** Function for the initialisation of the UI.
 **
 ** @param	argc	number of arguments
 ** @param	argv	arguments
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::init(int& argc, char**& argv)
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->init(argc, argv);

  this->ui->init(argc, argv);

  return ;
} // UI_Wrap::init(argc, argv)

/**
 ** updates the UI
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::update()
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->update();

  this->ui->update();

  return ;
} // void UI_Wrap::update()

/**
 ** sleeps the given time
 ** (in miliseconds, UINT_MAX for infinity)
 **
 ** @param	sleep_usec	time to sleep
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::sleep(unsigned const sleep_usec)
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->sleep(sleep_usec);

  this->ui->sleep(sleep_usec);

  return ;
} // void UI_Wrap::sleep(unsigned const sleep_usec)

/**
 ** all language elements of the UI shall be updated
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::language_update()
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->language_update();

  this->ui->language_update();

  return ;
} // void UI_Wrap::language_update()

/**
 ** the party is opened
 **
 ** @param	party	party that is opened
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::party_open(Party& party)
{
  this->UI::party_open(party);

  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->party_open(party);

  this->ui->party_open(party);

  return ;
} // void UI_Wrap::party_open(Party& party)

/**
 ** gets and sets the settings of the party
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::party_get_settings()
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->party_get_settings();

  this->ui->party_get_settings();

  return ;
} // void UI_Wrap::party_get_Settings()

/**
 ** the party is loaded
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.9
 **/
void
UI_Wrap::party_loaded()
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->party_loaded();

  this->ui->party_loaded();

  return ;
} // void UI_Wrap::party_loaded()

/**
 ** start of the party
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::party_start()
{ 
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->party_start();

  this->ui->party_start();

  return ;
} // void UI_Wrap::party_start()

/**
 ** a new round is started
 **
 ** @param	round	round that is started
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::party_start_round(unsigned const round)
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->party_start_round(round);

  this->ui->party_start_round(round);
}

/**
 ** end of the party
 ** (p.e. to show the points and the winner)
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::party_finish()
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->party_finish();

  this->ui->party_finish();

  return ;
} // void UI_Wrap::party_end()

/**
 ** the party will close
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::party_close()
{
  this->UI::party_close();

  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->party_close();

  this->ui->party_close();

  return ;
} // void UI_Wrap::party_close()

/**
 ** a game is opened
 **
 ** @param	game	game that is opened
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::game_open(Game& game)
{
  this->UI::game_open(game);

  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->game_open(game);

  this->ui->game_open(game);

  return ;
} // void UI_Wrap::game_open(Game& game)

/**
 ** the cards are distributed
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.8
 **/
void
UI_Wrap::game_cards_distributed()
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->game_cards_distributed();

  this->ui->game_cards_distributed();

  return ;
} // void UI_Wrap::game_cards_distributed()

/**
 ** the game is redistributed
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7b
 **/
void
UI_Wrap::game_redistribute()
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->game_redistribute();

  this->ui->game_redistribute();

  return ;
} // void UI_Wrap::game_redistribute()

/**
 ** gets the reservations of the player 'player'
 ** Here is the first time, the hands can be shown (and should)
 **
 ** @param	player	the player that makes the reservation
 **
 ** @return	Reservation of the player 'player'
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
Reservation
UI_Wrap::reservation_get(Player const& player)
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->reservation_get(player);

  return this->ui->reservation_get(player);
} // Reservation UI_Wrap::reservation_get(player)

/**
 ** the game is started
 ** (p.e. show the announcements of the other players)
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::game_start()
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->game_start();

  this->ui->game_start();

  return ;
} // void UI_Wrap::game_start()

/**
 ** the game is finished
 ** (p.e. show the winner and the points of the game)
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::game_finish()
{ 
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->game_finish();

  this->ui->game_finish();

  return ;
} // void UI_Wrap::game_finish()

/**
 ** the game will close
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::game_close()
{
  this->UI::game_close();

  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->game_close();

  this->ui->game_close();

  return ;
} // void UI_Wrap::game_close()

/**
 ** a new trick is opened
 **
 ** @param	trick	trick that is opened
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::trick_open(Trick const& trick)
{
  this->UI::trick_open(trick);

  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->trick_open(trick);

  this->ui->trick_open(trick);

  return ;
} // void UI_Wrap::trick_open(Trick const& trick)

/**
 ** gets the card, the player wishes to play
 ** (don't remove it from the hand!)
 **
 ** @param	player	the player who shall play a card
 **
 ** @return	Card to be played
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
HandCard
UI_Wrap::card_get(Player const& player)
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->card_get(player);

  return this->ui->card_get(player);
} // HandCard UI_Wrap::card_get(Player const& player)

/**
 ** the player 'player' plays the card 'card'
 **
 ** @param	card  	the played card
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::card_played(HandCard const& card)
{ 
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->card_played(card);

  this->ui->card_played(card);

  return ;
} // void UI_Wrap::card_played(HandCard const& card)

/**
 ** the announcement 'announcement' has been made by player 'player'
 **
 ** @param	announcement	the announcement
 ** @param	player		the player, who has made the announcement
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::announcement_made(Announcement const& announcement,
			   Player const& player)
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->announcement_made(announcement, player);

  this->ui->announcement_made(announcement, player);

  return ;
} // void UI_Wrap::announcement_made(Announcement const& announcement, Player const& player)

/**
 ** the player has swines
 **
 ** @param	player		the player with the swines
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::swines_announced(Player const& player)
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->swines_announced(player);

  this->ui->swines_announced(player);

  return ;
} // void UI_Wrap::swines_announced(Player const& player)

/**
 ** the player has hyperswines
 **
 ** @param	player		the player with the swines
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::hyperswines_announced(Player const& player)
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->hyperswines_announced(player);

  this->ui->hyperswines_announced(player);

  return ;
} // void UI_Wrap::hyperswines_announced(Player const& player)

/**
 ** the ai tests the card 'card'
 **
 ** @param	card		card to test
 ** @param	playerno	number of the player who plays the card
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.8
 **/
void
UI_Wrap::ai_test_card(Card const& card, unsigned const playerno)
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->ai_test_card(card, playerno);

  this->ui->ai_test_card(card, playerno);

  return ;
} // void UI_Wrap::ai_test_card(Card car, unsigned playerno)

/**
 ** the ai has calculated the weighting 'weighting' for the tested card
 **
 ** @param	weighting	calculated weighting
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.8
 **/
void
UI_Wrap::ai_card_weighting(int const weighting)
{
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->ai_card_weighting(weighting);

  this->ui->ai_card_weighting(weighting);

  return ;
} // void UI_Wrap::ai_card_weighting(int weighting)

/**
 ** virtual game: the player 'player' plays the card 'card'
 **
 ** @param	card  	the played card
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.8
 **/
void
UI_Wrap::virtual_card_played(HandCard const& card)
{ 
  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->virtual_card_played(card);

  this->ui->virtual_card_played(card);

  return ;
} // void UI_Wrap::virtual_card_played(HandCard card)

/**
 ** virtual game: the trick 'trick' is full
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.8
 **/
void
UI_Wrap::virtual_trick_full()
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->virtual_trick_full();

  this->ui->virtual_trick_full();

  return ;
} // void UI_Wrap::virtual_trick_full()

/**
 ** 'player' has a poverty and shifts cards
 **
 ** @param	player	the player who has the poverty
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::poverty_shifting(Player const& player)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->poverty_shifting(player);

  this->ui->poverty_shifting(player);

  return ;
} // void UI_Wrap::poverty_shifting(Player const& player)

/**
 ** 'player' shifts 'cardno' cards
 **
 ** @param	player	the player who shifts the cards
 ** @param	cardno	the number of cards that are shifted
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::poverty_shift(Player const& player, unsigned const cardno)
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->poverty_shift(player, cardno);

  this->ui->poverty_shift(player, cardno);

  return ;
} // void UI_Wrap::poverty_shift(Player const& player, unsigned const cardno)

/**
 ** ask 'player' whether to accept the poverty
 **
 ** @param	player	the player who is asked
 ** @param	cardno	number of cards that are given back
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::poverty_ask(Player const& player, unsigned const cardno)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->poverty_ask(player, cardno);

  this->ui->poverty_ask(player, cardno);

  return ;
} // void UI_Wrap::poverty_ask(Player const& player, unsigned const cardno)

/**
 ** 'player' denied to take the shifted cards
 **
 ** @param	player	the player who has denied to take the cards
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::poverty_take_denied(Player const& player)
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->poverty_take_denied(player);

  this->ui->poverty_take_denied(player);

  return ;
} // void UI_Wrap::poverty_take_denied(Player const& player)

/**
 ** all players have denied to take the cards
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::poverty_take_denied_by_all()
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->poverty_take_denied_by_all();

  this->ui->poverty_take_denied_by_all();

  return ;
} // void UI_Wrap::poverty_take_denied_by_all()

/**
 ** 'player' accepts to take the shifted cards
 ** and returns 'cardno' cards with 'trumpno' trumps
 **
 ** @param	player	the player who has denied to take the cards
 ** @param	cardno	number of cards that are given back
 ** @param	trumpno	number of trumps of the cards
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::poverty_take_accepted(Player const& player,
			       unsigned const cardno, unsigned const trumpno)
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->poverty_take_accepted(player, cardno, trumpno);

  this->ui->poverty_take_accepted(player, cardno, trumpno);

  return ;
} // void UI_Wrap::poverty_take_accepted(Player const& player, unsigned const cardno, unsigned const trumpno)

/**
 ** returns which cards the player shifts
 **
 ** @param	player	the player who shifts the cards
 **
 ** @return	the cards that are to be shifted
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
HandCards
UI_Wrap::poverty_shift(Player& player)
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->poverty_shift(player);

  return this->ui->poverty_shift(player);
} // HandCards UI_Wrap::poverty_shift(Player const& player)

/**
 ** returns whether 'player' accepts the shifted cards
 **
 ** @param	player	the player who shifts the cards
 ** @param	cardno	the number of shifted cards
 **
 ** @return	whether to accept the cards
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
bool
UI_Wrap::poverty_take_accept(Player& player, unsigned const cardno)
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->poverty_take_accept(player, cardno);

  return this->ui->poverty_take_accept(player, cardno);
} // void UI_Wrap::poverty_take_accept(Player const& player, unsigned const cardno)

/**
 ** changes the cards from the poverty-player
 **
 ** @param	player	the player who has accepted the cards
 ** @param	cards	the cards that are given to the player
 **
 ** @return	the cards that are returned to the poverty-player
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
HandCards
UI_Wrap::poverty_cards_change(Player& player, HandCards const& cards)
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->poverty_cards_change(player, cards);

  return this->ui->poverty_cards_change(player, cards);
} // HandCards UI_Wrap::poverty_cards_change(Player& player, HandCards const& cards)

/**
 ** the poverty player 'player' gets 'cards'
 **
 ** @param	player	the player gets the cards
 ** @param	cards	the cards that are given to the player
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::poverty_cards_get_back(Player& player, HandCards const& cards)
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->poverty_cards_get_back(player, cards);

  return this->ui->poverty_cards_get_back(player, cards);
} // void UI_Wrap::poverty_cards_get_back(Player& player, HandCards const& cards)

/**
 ** marriage: Information of the new team
 ** if the bride is the bridegroom, the bridegroom must play a solo
 **
 ** @param	bridegroom	the player with the marriage
 ** @param	bride		the bride
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.7.1
 **/
void
UI_Wrap::marriage(Player const& bridegroom,
		  Player const& bride)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->marriage(bridegroom, bride);

  this->ui->marriage(bridegroom, bride);

  return ;
} // void UI_Wrap::marriage(Player const& bridegroom, Player const& bride)

/**
 ** genscher: -> result
 **
 ** @param	-
 **
 ** @return	pointer to the new teammate,
 **		NULL if the genscher is not to be announced
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
Player const*
UI_Wrap::genscher_partner()
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->genscher_partner();

  return this->ui->genscher_partner();
} // Player const* UI_Wrap::genscher_partner()

/**
 ** genscher: Information of the new team
 **
 ** @param	player	genscher player
 ** @param	partner	partner of the gensher player
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::genscher(Player const& player,
		  Player const& partner)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->genscher(player, partner);

  this->ui->genscher(player, partner);

  return ;
} // void UI_Wrap::genscher(Player const& player, Player const& partner)

/**
 ** the trick 'trick' is full
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::trick_full()
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->trick_full();

  this->ui->trick_full();

  return ;
} // void UI_Wrap::trick_full()

/**
 ** moves the trick in the pile of the winnerplayer
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::trick_move_in_pile()
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->trick_move_in_pile();

  this->ui->trick_move_in_pile();

  return ;
} // void UI_Wrap::trick_move_in_pile()

/**
 ** the trick is closed
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::trick_close()
{
  this->UI::trick_close();

  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->trick_close();

  this->ui->trick_close();

  return ;
} // void UI_Wrap::trick_close()

/**
 ** redraw all
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::redraw_all()
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->redraw_all();

  this->ui->redraw_all();

  return ;
} // void UI_Wrap::redraw_all()

/**
 ** the players 'player_a' and 'player_b' have been switched
 **
 ** @param	player_a   first player
 ** @param	player_b   second player
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.7.2
 **/
void
UI_Wrap::players_switched(Player const& player_a, Player const& player_b)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->players_switched(player_a, player_b);

  this->ui->players_switched(player_a, player_b);

  return ;
} // void UI_Wrap::players_switched(Player player_a, Player player_b)

/**
 ** the player 'player' has to be updated
 **
 ** @param	player	the player
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::player_update(Player const& player)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->player_update(player);

  this->ui->player_update(player);

  return ;
} // void UI_Wrap::player_update(player)

/**
 ** the name of the player 'player' has to be updated
 **
 ** @param	player	the player, whose name is changed
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::name_update(Player const& player)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->name_update(player);

  this->ui->name_update(player);

  return ;
} // void UI_Wrap::name_update(player)

/**
 ** the hand of the player 'player' has to be updated
 **
 ** @param	player	the player, whose hand is to be updated
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::hand_update(Player const& player)
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->hand_update(player);

  this->ui->hand_update(player);

  return ;
} // void UI_Wrap::hand_update(player)

/**
 ** the teaminfo of the player 'player' has to be updated
 **
 ** @param	player	the player whose team should be updated
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::teaminfo_update(Player const& player)
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->teaminfo_update(player);

  this->ui->teaminfo_update(player);

  return ;
} // void UI_Wrap::team_udpate(player)

/**
 ** the gametype has to be updated
 ** (take the player from 'game.soloplayer()'
 **
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::gametype_update()
{ 
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->gametype_update();

  this->ui->gametype_update();

  return ;
} // void UI_Wrap::gametype_udpate()

/**
 ** the rule 'type' has changed
 **
 ** @param	type		the type that has changed
 ** @param	old_value	old value
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::rule_update(int const type, void const* const old_value)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->rule_update(type, old_value);

  this->ui->rule_update(type, old_value);

  return ;
} // void UI_Wrap::rule_update(int const type, void const* const old_value)

/**
 ** the setting 'type' has changed
 **
 ** @param	type		the type that has changed
 ** @param	old_value	old value
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::setting_update(int const type, void const* const old_value)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->setting_update(type, old_value);

  this->ui->setting_update(type, old_value);

  return ;
} // void UI_Wrap::setting_update(int const type, void const* const old_value)

/**
 ** a bug report replay is opened
 **
 ** @param	bug_report_replay	bug report replay that is opened
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.8
 **/
void
UI_Wrap::bug_report_replay_open(OS_NS::BugReportReplay const& bug_report_replay)
{
  this->UI::bug_report_replay_open(bug_report_replay);

  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->bug_report_replay_open(bug_report_replay);

  this->ui->bug_report_replay_open(bug_report_replay);

  return ;
} // void UI_Wrap::bug_report_replay_open(OS_NS::BugReportReplay bug_report_replay)

/**
 ** a bug report replay is closed
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.8
 **/
void
UI_Wrap::bug_report_replay_close()
{
  this->UI::bug_report_replay_close();

  list<OS*> oss = this->os;
  
  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->bug_report_replay_close();

  this->ui->bug_report_replay_close();

  return ;
} // void UI_Wrap::bug_report_replay_close()

/**
 ** load the page with the help
 **
 ** @param	page	the page to be loaded
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::help_load(string const& page)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->help_load(page);

  this->ui->help_load(page);

  return ;
}

/**
 ** 'player' has chatted 'message'
 **
 ** @param	player	the name of the player who has chatted
 ** @param	message	the chat message
 ** @param	self	whether this player has chattet
 **			(else the chatter comes from the network)
 **			default: true
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::chat(string const& player, string const& message, bool const self)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->chat(player, message, self);

  this->ui->chat(player, message, self);

  return ;
}

#ifdef USE_NETWORK

/**
 ** the listener 'listener' was opened
 **
 ** @param	listener	new listener
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.7.0
 **/
void
UI_Wrap::network_listener_new(Network::Listener const& listener)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->network_listener_new(listener);

  this->ui->network_listener_new(listener);

  return ;
}

/**
 ** the listener 'listener' was deleted
 **
 ** @param	listener	deleted listener
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.7.0
 **/
void
UI_Wrap::network_listener_deleted(Network::Listener const& listener)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->network_listener_deleted(listener);

  this->ui->network_listener_deleted(listener);

  return ;
}

/**
 ** the connection 'connection' was opened
 **
 ** @param	connection	new connection
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.7.0
 **/
void
UI_Wrap::network_connection_new(Network::Connection const& connection)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->network_connection_new(connection);

  this->ui->network_connection_new(connection);

  return ;
}

/**
 ** the connection 'connection' was changed
 **
 ** @param	connection	connection that was changed
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.7.0
 **/
void
UI_Wrap::network_connection_changed(Network::Connection const& connection)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->network_connection_changed(connection);

  this->ui->network_connection_changed(connection);

  return ;
}

/**
 ** the connection 'connection' was deleted
 **
 ** @param	connection	deleted connection
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.7.0
 **/
void
UI_Wrap::network_connection_deleted(Network::Connection const& connection)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->network_connection_deleted(connection);

  this->ui->network_connection_deleted(connection);

  return ;
}

/**
 **
 ** @param	connection	connection with the traffic
 ** @param	traffic_type	the traffic type
 ** @param	text		send text
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.7.0
 **/
void
UI_Wrap::network_traffic(Network::Connection const& connection,
			 Network::TrafficType const traffic_type,
			 string const& text)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->network_traffic(connection, traffic_type, text);

  this->ui->network_traffic(connection, traffic_type, text);

  return ;
}
#endif

/**
 **
 ** @param	message	the status message
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::status_message_changed(Translator::Translation const& message)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->status_message_changed(message);

  this->ui->status_message_changed(message);

  return ;
}

/**
 ** the program is busy
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::set_busy()
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->set_busy();

  this->ui->set_busy();

  return ;
}

/**
 ** the program is not busy any more
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::set_not_busy()
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->set_not_busy();

  this->ui->set_not_busy();

  return ;
}

/**
 ** the progress has changed
 **
 ** @param	progress	the progress
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::progress_changed(double const progress)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->progress_changed(progress);

  this->ui->progress_changed(progress);

  return ;
}

/**
 ** the progress is finished
 **
 ** @param	-
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::progress_finished()
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->progress_finished();

  this->ui->progress_finished();

  return ;
}

/**
 ** this is the first run of the program
 **
 ** @param	message		message for the user
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.7.0
 **/
void
UI_Wrap::first_run(Translator::Translation const& message)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->first_run(message);

  this->ui->first_run(message);

  return ;
}

/**
 ** the program is updated
 **
 ** @param	old_version	the old version
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.7.0
 **/
void
UI_Wrap::program_updated(DK::Utils::Version const& old_version)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->program_updated(old_version);

  this->ui->program_updated(old_version);

  return ;
}

/**
 ** information for the user
 **
 ** @param	message		message for the user
 ** @param	type		the type of information
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.9
 **/
void
UI_Wrap::information(Translator::Translation const& message,
		     INFORMATION::Type const type)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->information(message, type);

  this->ui->information(message, type);

  return ;
}

/**
 ** an error has occured
 **
 ** @param	message		message with the error description (hopefully)
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::error(string const& message)
{
  list<OS*> oss = this->os;

  for (list<OS*>::iterator os = oss.begin(); os != oss.end(); os++)
    (*os)->error(message);

  this->ui->error(message);

  return ;
}

/**
 ** sets the ui that is wrapped
 **
 ** @param	ui	the wrapped ui
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::ui_set(UI* const ui)
{ 
  delete this->ui;
  this->ui = ui;

  return ;
} // void UI_Wrap::ui_set(UI* const ui)

/**
 ** add the os to the wrapped os's
 **
 ** @param	os	os to be prepended
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.8
 **/
void
UI_Wrap::prepend(OS* const os)
{ 
  this->os.push_front(os);

  return ;
} // void UI_Wrap::prepend(OS* const os)

/**
 ** add the os to the wrapped os's
 **
 ** @param	os	os to be appended
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::append(OS* const os)
{ 
  this->os.push_back(os);

  return ;
} // void UI_Wrap::append(OS* const os)

/**
 ** remove 'os' from the wrapped 'os's
 **
 ** @param	os	os to be removeed
 **
 ** @return	-
 **
 ** @author	Diether Knof
 **
 ** @version	0.6.7
 **/
void
UI_Wrap::remove(OS* const os)
{ 
  for (list<OS*>::iterator os_it = this->os.begin();
       os_it != this->os.end();
       os_it++)
    if (*os_it == os) {
      this->os.erase(os_it);
      break;
    } // if (*os_it == os) 

  return ;
} // void UI_Wrap::remove(OS* const os)
