1 /**********************************************************************
2  *
3  *   FreeDoko a Doppelkopf-Game
4  *
5  *   Copyright (C) 2001 – 2018 by Diether Knof and Borg Enders
6  *
7  *   This program is free software; you can redistribute it and/or
8  *   modify it under the terms of the GNU General Public License as
9  *   published by the Free Software Foundation; either version 2 of
10  *   the License, or (at your option) any later version.
11  *
12  *   This program is distributed in the hope that it will be useful,
13  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  *   GNU General Public License for more details.
16  *   You can find this license in the file 'gpl.txt'.
17  *
18  *   You should have received a copy of the GNU General Public License
19  *   along with this program; if not, write to the Free Software
20  *   Foundation, Inc., 59 Temple Place, Suite 330, Boston,
21  *   MA  02111-1307  USA
22  *
23  *  Contact:
24  *    Diether Knof dknof@posteo.de
25  *
26  **********************************************************************/
27 
28 #pragma once
29 
30 #include "../basetypes.h"
31 #include "hand_cards.h"
32 class Trick;
33 class Player;
34 class SortedHand;
35 class SortedHandConst;
36 
37 /**
38  ** Hand (of a player) with all cards (played and not played)
39  **/
40 class Hand {
41   public:
42     using Position = unsigned;
43   public:
44     using const_iterator = HandCards::const_iterator;
45 
46     Hand() = default;
47     explicit Hand(Player const& player);
48     Hand(Player const& player, Hand const& h);
49     explicit Hand(vector<Card> const& cards);
50     Hand(Player const& player, vector<Card> const& cards);
51     Hand(Player const& player, vector<Card> const& unplayed_cards,
52          vector<Card> const& played_cards);
53     explicit Hand(string const& text);
54     explicit Hand(istream& istr);
55     Hand(Hand const& h);
56     Hand& operator=(Hand const& h);
57 
58     ~Hand() = default;
59 
60     operator HandCards() const;
61     operator vector<Card>() const;
62     const_iterator begin() const;
63     const_iterator end() const;
64 
65     HandCards const& cards() const;
66     SortedHand sorted();
67     SortedHandConst sorted() const;
68 
69     bool self_check() const;
70 
71     Player const& player() const;
72     void set_player(Player const& player);
73 
74     Game const& game() const;
75 
76     bool empty() const;
77     size_t cardsnumber() const;
78     size_t cardsnumber_all() const;
79 
80     unsigned points() const;
81 
82     void set_known(Card card, unsigned n = 1);
83 
84     HandCard const& card(unsigned i) const;
85     HandCard const& card_all(unsigned i) const;
86     bool played(unsigned i) const;
87     unsigned played_trick(unsigned i) const;
88 
89     HandCards cards_single() const;
90     map<Card, unsigned> counted_cards() const;
91 
92     Card::Value highest_value() const;
93     Card::Value highest_value(Card::TColor const tcolor) const;
94     Card::Value lowest_value() const;
95     Card::Value lowest_value(Card::TColor const tcolor) const;
96 
97     HandCard const& highest_card() const;
98     HandCard const& highest_trump() const;
99     HandCard const& highest_trump_till(Card card_limit) const;
100     HandCard const& highest_card(Card::TColor const tcolor) const;
101     HandCard const& lowest_trump() const;
102     HandCard const& lowest_card(Card::TColor const tcolor) const;
103     bool higher_card_exists(Card card) const;
104     bool lower_card_exists(Card card) const;
105     unsigned higher_cards_no(Card card) const;
106     HandCard const& next_jabbing_card(Card card) const;
107     HandCard const& next_higher_card(Card card) const;
108     HandCard const& same_or_higher_card(Card card) const;
109     HandCard const& next_lower_card(Card card) const;
110     HandCard const& same_or_lower_card(Card card) const;
111     bool can_jab(Trick const& trick) const;
112 
113     unsigned getpos(Card card) const;
114     unsigned getpos_all(Card card) const;
115 
116     // transform the position in the unplayed cards to the position in all cards
117     unsigned pos_to_pos_all(unsigned pos) const;
118     // transform the position in all cards to the position in the unplayed cards
119     unsigned pos_all_to_pos(unsigned pos) const;
120 
121 
122 
123     // changing
124 
125     void playcard(Card card);
126     void playcard(unsigned pos);
127     void unplaycard(Card card);
128 
129     void add(Card card, unsigned n = 1);
130     void add(vector<Card> const& cards);
131     void add(Hand const& hand);
132 
133     void add_played(Card card, unsigned n = 1);
134     void add_played(vector<Card> const& cards);
135 
136     void remove(Position position);
137     void remove(HandCard const& card);
138     void remove(Card card);
139     void remove(HandCards const& cards);
140     void remove_all(Card card);
141     void remove_all(std::initializer_list<Card> const& cards);
142     void remove_played_cards();
143 
144 
145 
146     // card request
147 
148     unsigned requested_position() const;
149     HandCard requested_card() const;
150     unsigned requested_position_all() const;
151     void request_position(unsigned position);
152     void request_position_all(unsigned position_all);
153     void request_card(Card card);
154     void forget_request();
155 
156 
157 
158     // counting
159 
160     HandCards validcards(Trick const& trick) const;
161     // the cards of a given tcolor (only one of them)
162     HandCards single_cards(Card::TColor tcolor) const;
163     // the cards of a given tcolor
164     HandCards cards(Card::TColor tcolor) const;
165     HandCards cards(Card::TColor tcolor, GameType game_type) const;
166     // the trumps
167     HandCards single_trumps() const;
168 
169     bool hastrump() const;
170     bool hascolor() const;
171 
172     bool has_possible_genscher() const;
173     bool has_swines() const;
174     bool has_hyperswines() const;
175 
176     unsigned count(Card::Value value) const;
177     unsigned count_rich_cards() const;
178     unsigned count(Card::TColor tcolor) const;
179     unsigned count(Card card) const;
180     unsigned count(Card::TColor tcolor,
181                    Card::Value value) const;
182 
183     unsigned count(Card::Color color, Game const& game) const;
184     unsigned count(Card::Color color,
185                    GameType gametype) const;
186     unsigned count(Card::Color color,
187                    GameType gametype,
188                    bool dullen) const;
189     unsigned count_fehl() const;
190     unsigned count_fehl_colors(GameType game_type) const;
191 
192     unsigned count_played() const;
193     unsigned played(Card card) const;
194 
195     unsigned count_trumps() const;
196     unsigned count_trumps(GameType game_type) const;
197     unsigned count_single_tens(GameType game_type) const;
198     unsigned count_trump_aces() const;
199     unsigned count_trump_aces(GameType game_type) const;
200     unsigned count_trump_nines() const;
201     unsigned count_trump_kings() const;
202     unsigned count_nines() const;
203     unsigned count_kings() const;
204     unsigned count_club_queens() const;
205     unsigned count_dulle() const;
206     unsigned count_swines() const;
207     unsigned count_hyperswines() const;
208 
209     unsigned count_poverty_cards() const;
210     bool has_poverty() const;
211 
212     unsigned count_all(Card::TColor tcolor, Card::Value value) const;
213     unsigned count_all(Card card) const;
214     unsigned count_all_trump_aces() const;
215 
216 
217     unsigned count_ge(Card card) const;
218     unsigned count_le(Card card) const;
219     unsigned count_ge_trump(Card card) const;
220     unsigned count_le_trump(Card card) const;
221     float rel_pos_trump(Card card) const;
222 
223     // checking
224 
225     bool has_same_cards(Hand const& hand) const;
226 
227     bool contains(Card::TColor tcolor) const;
228     bool contains(Card card) const;
229     bool contains(Card::Color color, Card::Value value) const;
230     bool contains(Hand const& hand) const;
231     HandCards missing_cards(Hand const& hand) const;
232 
233     bool contains_ten_points_in_trump() const;
234 
235     bool contains_unknown_or_played() const;
236 
237   private:
238     HandCards cards_;
239     HandCards cards_all_;
240     // whether a card is played and in which trick
241     vector<unsigned> played_;
242 
243     unsigned requested_position_ = UINT_MAX;
244 
245     Player const* player_ = nullptr;
246 };
247 
begin(Hand const & hand)248 inline auto begin(Hand const& hand)
249 { return hand.begin(); }
end(Hand const & hand)250 inline auto end(Hand const& hand)
251 { return hand.end(); }
252 
253 ostream& operator<<(ostream& ostr, Hand const& hand);
254 
255 bool operator==(Hand const& lhs, Hand const& rhs);
256 bool operator!=(Hand const& lhs, Hand const& rhs);
257