renaming and moving samples around
[wxWidgets.git] / demos / forty / card.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: card.cpp
3 // Purpose: Forty Thieves patience game
4 // Author: Chris Breeze
5 // Modified by:
6 // Created: 21/07/97
7 // RCS-ID: $Id$
8 // Copyright: (c) 1993-1998 Chris Breeze
9 // Licence: wxWindows licence
10 //---------------------------------------------------------------------------
11 // Last modified: 22nd July 1998 - ported to wxWindows 2.0
12 /////////////////////////////////////////////////////////////////////////////
13 //+-------------------------------------------------------------+
14 //| Description
15 //| A class for drawing playing cards.
16 //| Currently assumes that the card symbols have been
17 //| loaded into hbmap_symbols and the pictures for the
18 //| Jack, Queen and King have been loaded into
19 //| hbmap_pictures.
20 //+-------------------------------------------------------------+
21
22 #ifdef __GNUG__
23 #pragma implementation
24 #pragma interface
25 #endif
26
27 // For compilers that support precompilation, includes "wx/wx.h".
28 #include "wx/wxprec.h"
29
30 #ifdef __BORLANDC__
31 #pragma hdrstop
32 #endif
33
34 #ifndef WX_PRECOMP
35 #include "wx/wx.h"
36 #endif
37
38 #include <stdlib.h>
39 #include <stdio.h>
40 #include <string.h>
41 #include "forty.h"
42 #include "card.h"
43
44 #if defined(__WXGTK__) || defined(__WXMOTIF__) || defined(__WXMAC__)
45 #include "pictures.xpm"
46 #include "symbols.xbm"
47 #endif
48
49 wxBitmap* Card::m_pictureBmap = 0;
50 wxBitmap* Card::m_symbolBmap = 0;
51
52
53 //+-------------------------------------------------------------+
54 //| Card::Card() |
55 //+-------------------------------------------------------------+
56 //| Description: |
57 //| Constructor for a playing card. |
58 //| Checks that the value is in the range 1..52 and then |
59 //| initialises the suit, colour, pipValue and wayUp. |
60 //+-------------------------------------------------------------+
61 Card::Card(int value, WayUp way_up) :
62 m_wayUp(way_up)
63 {
64 if (!m_symbolBmap)
65 {
66 #ifdef __WXMSW__
67 m_symbolBmap = new wxBitmap("CardSymbols", wxBITMAP_TYPE_BMP_RESOURCE);
68 #else
69 m_symbolBmap = new wxBitmap(Symbols_bits, Symbols_width, Symbols_height);
70 #endif
71 if (!m_symbolBmap->Ok())
72 {
73 ::wxMessageBox("Failed to load bitmap CardSymbols", "Error");
74 }
75 }
76 if (!m_pictureBmap)
77 {
78 #ifdef __WXMSW__
79 m_pictureBmap = new wxBitmap("CardPictures", wxBITMAP_TYPE_BMP_RESOURCE);
80 #else
81 m_pictureBmap = new wxBitmap(Pictures);
82 #endif
83 if (!m_pictureBmap->Ok())
84 {
85 ::wxMessageBox("Failed to load bitmap CardPictures", "Error");
86 }
87 }
88
89 if (value >= 1 && value <= PackSize)
90 {
91 switch ((value - 1) / 13)
92 {
93 case 0:
94 m_suit = clubs;
95 m_colour = black;
96 break;
97 case 1:
98 m_suit = diamonds;
99 m_colour = red;
100 break;
101 case 2:
102 m_suit = hearts;
103 m_colour = red;
104 break;
105 case 3:
106 m_suit = spades;
107 m_colour = black;
108 break;
109 }
110 m_pipValue = 1 + (value - 1) % 13;
111 m_status = TRUE;
112 }
113 else
114 {
115 m_status = FALSE;
116 }
117 } // Card::Card()
118
119
120 //+-------------------------------------------------------------+
121 //| Card::~Card() |
122 //+-------------------------------------------------------------+
123 //| Description: |
124 //| Destructor - nothing to do at present. |
125 //+-------------------------------------------------------------+
126 Card::~Card()
127 {
128 }
129
130
131 //+-------------------------------------------------------------+
132 //| Card::Erase() |
133 //+-------------------------------------------------------------+
134 //| Description: |
135 //| Erase the card at (x, y) by drawing a rectangle in the |
136 //| background colour. |
137 //+-------------------------------------------------------------+
138 void Card::Erase(wxDC& dc, int x, int y)
139 {
140 wxPen* pen = wxThePenList->FindOrCreatePen(
141 FortyApp::BackgroundColour(),
142 1,
143 wxSOLID
144 );
145 dc.SetPen(* pen);
146 dc.SetBrush(FortyApp::BackgroundBrush());
147 dc.DrawRectangle(x, y, CardWidth, CardHeight);
148 } // Card::Erase()
149
150
151 //+-------------------------------------------------------------+
152 //| Card::Draw() |
153 //+-------------------------------------------------------------+
154 //| Description: |
155 //| Draw the card at (x, y). |
156 //| If the card is facedown draw the back of the card. |
157 //| If the card is faceup draw the front of the card. |
158 //| Cards are not held in bitmaps, instead they are drawn |
159 //| from their constituent parts when required. |
160 //| hbmap_symbols contains large and small suit symbols and |
161 //| pip values. These are copied to the appropriate part of |
162 //| the card. Picture cards use the pictures defined in |
163 //| hbmap_pictures. Note that only one picture is defined |
164 //| for the Jack, Queen and King, unlike a real pack where |
165 //| each suit is different. |
166 //| |
167 //| WARNING: |
168 //| The locations of these symbols is 'hard-wired' into the |
169 //| code. Editing the bitmaps or the numbers below will |
170 //| result in the wrong symbols being displayed. |
171 //+-------------------------------------------------------------+
172 void Card::Draw(wxDC& dc, int x, int y)
173 {
174 wxBrush backgroundBrush( dc.GetBackground() );
175 dc.SetBrush(* wxWHITE_BRUSH);
176 dc.SetPen(* wxBLACK_PEN);
177 dc.DrawRoundedRectangle(x, y, CardWidth, CardHeight, 4);
178 if (m_wayUp == facedown)
179 {
180 dc.SetBackground(* wxRED_BRUSH);
181 dc.SetBackgroundMode(wxSOLID);
182 wxBrush* brush = wxTheBrushList->FindOrCreateBrush(
183 "BLACK", wxCROSSDIAG_HATCH
184 );
185 dc.SetBrush(* brush);
186
187 dc.DrawRoundedRectangle(
188 x + 4, y + 4,
189 CardWidth - 8, CardHeight - 8,
190 2
191 );
192 }
193 else
194 {
195 wxMemoryDC memoryDC;
196 memoryDC.SelectObject(* m_symbolBmap);
197
198 // dc.SetBackgroundMode(wxTRANSPARENT);
199
200 dc.SetTextBackground(*wxWHITE);
201 switch (m_suit)
202 {
203 case spades:
204 case clubs:
205 dc.SetTextForeground(*wxBLACK);
206 break;
207 case diamonds:
208 case hearts:
209 dc.SetTextForeground(*wxRED);
210 break;
211 }
212 // Draw the value
213 dc.Blit(x + 3, y + 3, 6, 7,
214 &memoryDC, 6 * (m_pipValue - 1), 36, wxCOPY);
215 dc.Blit(x + CardWidth - 9, y + CardHeight - 11, 6, 7,
216 &memoryDC, 6 * (m_pipValue - 1), 43, wxCOPY);
217
218 // Draw the pips
219 dc.Blit(x + 11, y + 3, 7, 7,
220 &memoryDC, 7 * m_suit, 0, wxCOPY);
221 dc.Blit(x + CardWidth - 17, y + CardHeight - 11, 7, 7,
222 &memoryDC, 7 * m_suit, 7, wxCOPY);
223
224 switch (m_pipValue)
225 {
226 case 1:
227 dc.Blit(x - 5 + CardWidth / 2, y - 5 + CardHeight / 2, 11, 11,
228 &memoryDC, 11 * m_suit, 14, wxCOPY);
229 break;
230
231 case 3:
232 dc.Blit(x - 5 + CardWidth / 2, y - 5 + CardHeight / 2, 11, 11,
233 &memoryDC, 11 * m_suit, 14, wxCOPY);
234 case 2:
235 dc.Blit(x - 5 + CardWidth / 2,
236 y - 5 + CardHeight / 4, 11, 11,
237 &memoryDC, 11 * m_suit, 14, wxCOPY);
238 dc.Blit(x - 5 + CardWidth / 2,
239 y - 5 + 3 * CardHeight / 4, 11, 11,
240 &memoryDC, 11 * m_suit, 25, wxCOPY);
241 break;
242
243 case 5:
244 dc.Blit(x - 5 + CardWidth / 2, y - 5 + CardHeight / 2, 11, 11,
245 &memoryDC, 11 * m_suit, 14, wxCOPY);
246 case 4:
247 dc.Blit(x - 5 + CardWidth / 4,
248 y - 5 + CardHeight / 4, 11, 11,
249 &memoryDC, 11 * m_suit, 14, wxCOPY);
250 dc.Blit(x - 5 + CardWidth / 4,
251 y - 5 + 3 * CardHeight / 4, 11, 11,
252 &memoryDC, 11 * m_suit, 25, wxCOPY);
253 dc.Blit(x - 5 + 3 * CardWidth / 4,
254 y - 5 + CardHeight / 4, 11, 11,
255 &memoryDC, 11 * m_suit, 14, wxCOPY);
256 dc.Blit(x - 5 + 3 * CardWidth / 4,
257 y - 5 + 3 * CardHeight / 4, 11, 11,
258 &memoryDC, 11 * m_suit, 25, wxCOPY);
259 break;
260
261 case 8:
262 dc.Blit(x - 5 + 5 * CardWidth / 10,
263 y - 5 + 5 * CardHeight / 8, 11, 11,
264 &memoryDC, 11 * m_suit, 25, wxCOPY);
265 case 7:
266 dc.Blit(x - 5 + 5 * CardWidth / 10,
267 y - 5 + 3 * CardHeight / 8, 11, 11,
268 &memoryDC, 11 * m_suit, 14, wxCOPY);
269 case 6:
270 dc.Blit(x - 5 + CardWidth / 4,
271 y - 5 + CardHeight / 4, 11, 11,
272 &memoryDC, 11 * m_suit, 14, wxCOPY);
273 dc.Blit(x - 5 + CardWidth / 4,
274 y - 5 + CardHeight / 2, 11, 11,
275 &memoryDC, 11 * m_suit, 14, wxCOPY);
276 dc.Blit(x - 5 + CardWidth / 4,
277 y - 5 + 3 * CardHeight / 4, 11, 11,
278 &memoryDC, 11 * m_suit, 25, wxCOPY);
279 dc.Blit(x - 5 + 3 * CardWidth / 4,
280 y - 5 + CardHeight / 4, 11, 11,
281 &memoryDC, 11 * m_suit, 14, wxCOPY);
282 dc.Blit(x - 5 + 3 * CardWidth / 4,
283 y - 5 + CardHeight / 2, 11, 11,
284 &memoryDC, 11 * m_suit, 14, wxCOPY);
285 dc.Blit(x - 5 + 3 * CardWidth / 4,
286 y - 5 + 3 * CardHeight / 4, 11, 11,
287 &memoryDC, 11 * m_suit, 25, wxCOPY);
288 break;
289
290 case 10:
291 dc.Blit(x - 5 + CardWidth / 2,
292 y - 5 + 2 * CardHeight / 3, 11, 11,
293 &memoryDC, 11 * m_suit, 25, wxCOPY);
294 case 9:
295 dc.Blit(x - 5 + CardWidth / 4,
296 y - 6 + CardHeight / 4, 11, 11,
297 &memoryDC, 11 * m_suit, 14, wxCOPY);
298 dc.Blit(x - 5 + CardWidth / 4,
299 y - 6 + 5 * CardHeight / 12, 11, 11,
300 &memoryDC, 11 * m_suit, 14, wxCOPY);
301 dc.Blit(x - 5 + CardWidth / 4,
302 y - 5 + 7 * CardHeight / 12, 11, 11,
303 &memoryDC, 11 * m_suit, 25, wxCOPY);
304 dc.Blit(x - 5 + CardWidth / 4,
305 y - 5 + 3 * CardHeight / 4, 11, 11,
306 &memoryDC, 11 * m_suit, 25, wxCOPY);
307
308 dc.Blit(x - 5 + 3 * CardWidth / 4,
309 y - 6 + CardHeight / 4, 11, 11,
310 &memoryDC, 11 * m_suit, 14, wxCOPY);
311 dc.Blit(x - 5 + 3 * CardWidth / 4,
312 y - 6 + 5 * CardHeight / 12, 11, 11,
313 &memoryDC, 11 * m_suit, 14, wxCOPY);
314 dc.Blit(x - 5 + 3 * CardWidth / 4,
315 y - 5 + 7 * CardHeight / 12, 11, 11,
316 &memoryDC, 11 * m_suit, 25, wxCOPY);
317 dc.Blit(x - 5 + 3 * CardWidth / 4,
318 y - 5 + 3 * CardHeight / 4, 11, 11,
319 &memoryDC, 11 * m_suit, 25, wxCOPY);
320 dc.Blit(x - 5 + CardWidth / 2,
321 y - 5 + CardHeight / 3, 11, 11,
322 &memoryDC, 11 * m_suit, 14, wxCOPY);
323 break;
324 case 11:
325 case 12:
326 case 13:
327 memoryDC.SelectObject(* m_pictureBmap);
328 dc.Blit(x + 5, y - 5 + CardHeight / 4, 40, 45,
329 &memoryDC, 40 * (m_pipValue - 11), 0, wxCOPY);
330 memoryDC.SelectObject(* m_symbolBmap);
331 dc.Blit(x + 32, y - 3 + CardHeight / 4, 11, 11,
332 &memoryDC, 11 * m_suit, 14, wxCOPY);
333 dc.Blit(x + 7, y + 27 + CardHeight / 4, 11, 11,
334 &memoryDC, 11 * m_suit, 25, wxCOPY);
335 break;
336 }
337
338 }
339 dc.SetBackground( backgroundBrush );
340 } // Card:Draw()
341
342
343 //+-------------------------------------------------------------+
344 //| Card::DrawNullCard() |
345 //+-------------------------------------------------------------+
346 //| Description: |
347 //| Draws the outline of a card at (x, y). |
348 //| Used to draw place holders for empty piles of cards. |
349 //+-------------------------------------------------------------+
350 void Card::DrawNullCard(wxDC& dc, int x, int y)
351 {
352 wxPen* pen = wxThePenList->FindOrCreatePen(FortyApp::TextColour(), 1, wxSOLID);
353 dc.SetBrush(FortyApp::BackgroundBrush());
354 dc.SetPen(*pen);
355 dc.DrawRoundedRectangle(x, y, CardWidth, CardHeight, 4);
356 } // Card::DrawNullCard()
357
358