November 9, 2004 From: Bob Zale, President PowerBASIC, Inc. PowerBASIC Gazette #43 - Please share with fellow programmers ============================================================= Subject: So how can you display Playing Cards? =============================================== Graphics. Games. Amusement. An important part of Windows. But just where do you start on your trek to the next great adventure? For many, it's cards... playing cards... Whether your game is Blackjack, Texas Hold'em, Solitaire, or more, one big challenge is drawing those cards! Well, here's your solution! Thanks to Egbert Zijlema, a long-time PB programmer, we're pleased to present a quick and easy solution. A DLL roadmap for the bitmaps, and a tutorial to get you started! But more about that later. First, a short commercial message . {smile} Would you help spread the word about PowerBASIC? You know, you're the world's best PowerBASIC advertisement. And every time we add a PowerBASIC customer, it helps us all. Every new user is an investment in the future... with more users, we'll create better products, deliver them sooner, and keep the pricing right for you. How about it? Will you tell a friend about PowerBASIC? I hope so. We'll make it easy for you to "Share the Power"! Here's the plan... You give us a name (or a few names), and we'll send just one short, informative e-mail, using both your name and ours. We won't follow it up. In fact, we'll never use their e-mail again, unless they choose to sign up for The Gazette. So, Share the Power! Just GoTo... http://www.powerbasic.com/bin/ps.exe You'll see the text of the message and add a contact name! The message is harmless, yet informative. And just think of the compilers we could build for you if everyone brought just one new PowerBASIC user! Secure your PowerBASIC with a Backup CD ======================================================================= Downloads are great. Fast... Get your code now... Use it today. Patch updates are great. They're FREE to PB/CC 3.04 and PB/WIN 7.04. But sometimes, that's just not enough. You may need a real backup for security. You may want the entire installation on a single CD. Either way, we've got you covered... Backup CD's for $15 Of course, only registered owners can order {smile}, but it's a pretty small price to pay for the added security. You'll get a complete installation, the latest version of a product. It's burned on a registered CD, all for just $15. You can call, write, or just use the online order form at https://www.powerbasic.com/shop/ (Secure Server). Shipping by standard mail is just $4 worldwide. Using the playing cards library CARDS.DLL by Egbert Zijlema ======================================================================= This article deals with the creation of card games. More to the point, it discusses the issue of how to utilize the Application Programming Interface (API) for Windows' playing card library: CARDS.DLL To write a good and entertaining card game, a programmer may need more than this API alone. For some games, you may need a sufficient skill of drag and drop techniques, so the user can drag bitmaps (playing cards are bitmaps, after all) around a gaming table. This is a rather complex technique, and reaches beyond the scope of this article. In the first place because I am not an expert in that field, but also because knowledge of the playing cards API is an important first step on your way to writing card games. And always remember, one of the "official" games shipped with Windows, Free Cell, does not use drag and drop techniques at all. The playing card library contains five exported functions needed to draw or remove cards or card backs onto the device context of the window or dialog that represents the gaming table. For instance, this might be a LABEL control with the %SS_BITMAP style. The library file is CARDS.DLL, residing in the system directory and shipped with every version of Windows. But beware: in the beginning this file was 16-bit. This means that a 32-bit game created with the powerful PB for Windows compiler (PBWin) cannot utilize the default library. Generally speaking, this will be the case when either Windows 95, Windows 98 or Windows ME is your machines operating system. In 1996 Microsoft launched a 32-bit version of the cards library, named CARDS32.DLL. This file is still downloadable (for the URL see: footnotes) from Microsoft. But some question remains as to whether is it freely distributable to your customers, if they still use Win9X. In his MSDN column (Spring 1996) "Fun and Games", Microsoft editor Dave Edson refers to this issue as follows: "If you write a 32-bit game, you will need to install CARDS32.DLL on the user's machine." I don't know how to interpret this quote perfectly. Since Edson's column was specially written for Visual Basic programmers, it's possible his statement was only meant as a privelege for VB users. I just can't say for sure. Regardless, at least you can download and copy it to the system directory for your own use, if necessary. I also recommend using CARDS32.DLL when your OS is WinXP, because that library no longer supports animated card backs, such as: 1) Sun sticks tongue out 2) Moving robot meters 3) Flying bats around a castle 4) Card in/out magician's sleeve Another important note on CARDS.DLL: it is not always automatically installed with Windows. To check this, try playing a Windows card game like Solitaire or Free Cell. If you can't find shortcuts to them in the Start menu, you can be pretty sure that CARDS.DLL is missing too. If this is the case, you can install Windows' entertainment pack, or download the above mentioned CARDS32.DLL. Five exported functions: So far, it's been a handful of general remarks on CARDS(32).DLL. Now, it's time for more details. As I said before, the library has five (only 5!) exported functions. Two of them are only used once in your game (to start and to terminate), the others serve to draw cards, card backs, the pile indicator, the circle and red X, or to animate a card back. The following list shows the five declarations. Note that the library name used here is the default: CARDS.DLL. If you decide to use CARDS32.DLL, then change this appropriately in each. DECLARE FUNCTION CdtInit LIB "CARDS.DLL" ALIAS "cdtInit" (crdWidth AS LONG, _ crdHeight AS LONG) AS LONG DECLARE SUB CdtTerm LIB "CARDS.DLL" ALIAS "cdtTerm" () DECLARE FUNCTION CdtDraw LIB "CARDS.DLL" ALIAS "cdtDraw" (BYVAL hDC AS DWORD, _ BYVAL xPos AS LONG, BYVAL yPos AS LONG, BYVAL crdValue AS LONG, - BYVAL crdMode AS LONG, BYVAL bgColor AS LONG) AS LONG DECLARE FUNCTION CdtDrawExt LIB "CARDS.DLL" ALIAS "cdtDrawExt" (BYVAL hDC _ AS DWORD, BYVAL xPos AS LONG, BYVAL yPos AS LONG, BYVAL xCrd AS LONG, _ BYVAL yCrd AS LONG, BYVAL crdValue AS LONG, BYVAL crdMode AS LONG, _ BYVAL bgColor AS LONG) AS LONG DECLARE FUNCTION CdtAnimate LIB "CARDS.DLL" ALIAS "cdtAnimate" (BYVAL hDC _ AS DWORD, BYVAL idBack AS LONG, BYVAL x AS LONG, BYVAL y AS LONG, _ BYVAL lFrame AS LONG) AS LONG About cdtInit: This function takes two parameters, returning the default width (71 pixels) and height (96 pixels) of a card. This function is used only once, just to load the library. A good place to call this function is PBMain, because your application may want to utilize these dimensions to calculate the necessary width and height of the gaming table. Therefore, store the values returned by cdtInit as GLOBAL variables, which enables you to use them wherever you need them. About cdtTerm: Like cdtInit, this SUB is also used once in your card game, to unload the library just before your application quits. It does not take parameters. A good place to call it is the %WM_DESTROY message in the message pump, or (in case your application window is a DDT-created dialog) just before DIALOG END CBHNDL is called. About cdtDraw: This FUNCTION is the one that performs. It draws a card, removes a card, draws a card back, draws the red X ("no more card deals"), draws the circle ("pile empty"), and draws a transparent dotted layer on top of a card. It's action depends on the value of the crdMode parameter. The function takes 6 params: -hDC, the handle of the window's device context onto which the card will be drawn -xPos, the topleft x-position of the card being drawn -yPos, the topleft y-position -crdMode, specifies what is drawn: a card, a back, the red X, etc. 0 (%FACE_UP): draws the card specified in crdValue 1 (%FACE_DOWN): draws the card back specified in crdValue 2 (%HI_LITE): draws a specified card using inverted colors 3 (%ACE_PILE): draws a dotted pile indicator in bgColor 4 (%REMOVE): draws an "empty" card in bgColor 5 (%DOTTED_LAYER): draws a transparent dotted layer on the card 6 (%RED_X): draws the green card with the red X 7 (%CIRCLE): draws the green card with the circle -crdValue, specifies either a card (0 thru 51), or a card back (54 - 65). This parameter is ignored when crdMode is not 0, 1 or 2 -bgColor, only useful when crdMode = 3, 4, or 5; ignored in other modes About cdtDrawExt: Almost the same as cdtDraw, except that it draws cards and backs in a non-standard width and height. Therefore, this FUNCTION takes two extra parameters, the 4th (xCrd) and the 5th (yCrd), where the programmer must specify the dimensions. I really do not recommend using this function, as the cards are drawn with four sharp corners, which are not very attractive. There is one exception, though. If your game includes a routine to let the user specify a default card back, you can use cdtDrawExt to draw twelve %REMOVE-style rectangles that are a few pixels wider and taller than the default card dimensions. On top of each of these rectangles your program draws the card backs, using cdtDraw. Simply take care that the cardback's topleft position differs 1 or 2 pixels from that of the rectangles. And, of course: draw 11 of the rectangles in the gaming table's color, in order to make them invisible. The one 'behind' the selected card back should be drawn in a different color. Now your selection dialog will be displayed with a 'border' around the default card back. About cdtAnimate: Handles the animation frames of 4 card backs. This function has become obsolete since the launch of Windows XP, because the default library of that platform (CARDS.DLL) does not support animated card backs. In earlier 32-bit versions of CARDS.DLL and CARDS32.DLL, animation is supported for the following card backs: #56 (Robot meters), #63 (Flying bats), #64 (Sun sticks tongue out), and #65 (Card hand). The bats-back uses 2 frames, the others use 4, numbered 0 - 1 and 0 - 3 respectively. Insert a 250 milliseconds pause (SLEEP 250, in Power Basic) in between the frames in order to see a smooth animation. The function takes the following parameters: -hDC, handle of device context (same as in cdtDraw) -idBack, number of animated back (56, 63, 64 or 65) -x, card's topleft x-position -y, card's topleft y-position -lFrame, number of the frame (0 thru 1 or 0 thru 3) An example to animate "Sun sticks tongue out": FOR count% = 0 TO 3 cdtAnimate hDC, 64, x, y, count% SLEEP 250 NEXT About card faces and suits: The bitmap resource in CARDS(32).DLL contains 52 playing cards. They are identified as 0 (Ace of Clubs), 1 (Ace of Diamonds), 2 (Ace of Hearts), 3 (Ace of Spades) thru 51 (King of Spades). In other words: the 4 Aces come first, then the Two's, the Threes... up to the 4 Kings as 48, 49, 50 and 51 respectively. These are the values passed through the crdValue-param in cdtDraw. But how are these values computed? By this formula: crdValue = crdFace * 4 + crdSuit This means, we need to know the values for both the card faces and the suits. Originally, the faces are numbered 0 for an Ace through 12 for a King. This is not very natural, however, because normally an Ace is valued as 1 and a King as 13. Using these modified values allows us to utilize only a few (4) name constants or equates: %ACE = 1, %JACK = 11, %QUEEN = 12 and %KING = 13. The number cards are simply identified by their natural value, instead of such strange constant creations like %SEVEN = 6! The suits are identified as %CLUBS = 0, %DIAMONDS = 1, %HEARTS = 2 and %SPADES = 3. Now, assume we want to draw the 10 of Hearts. As said, in the library, a Ten has a value of 9. "Our" Ten values 10, so initially we need to substract 1 in order to get the Windows-value. This is the formula in pseudo-code: crdValue = (crdFace - 1) * 4 + crdSuit In real code: cdtDraw hDc, x, y, %FACE_UP, (10 - 1) * 4 + %HEARTS, clr (as said before, the color parameter is ignored here). A final thought, the alternate way: The techniques discussed so far, assume that the device context used to draw is the device context of the entire gaming table. You certainly need to do it this way if you want to implement drag and drop service in your game. However, if you are sure that you don't need that technique, you may prefer to use a control for each individual card displayed. This control, most likely a LABEL having the %SS_BITMAP style, is exactly as large as the card itself, so xPos and yPos are always 0. The benefit of this method is a far easier way to detect which card has been clicked: the card that occupies the control which received the %BN_CLICKED message (via %WM_COMMAND in the message pump). Footnotes: * CARDS32.DLL can be downloaded from: http://download.microsoft.com/download/2/1/8/2189d324-15cb-41e3-823f-406986cb80bd/games.exe * A working cards demo, created by the author, can be downloaded here: http://www.powerbasic.com/files/pub/pbwin/games (cards.zip) * An example of the alternate method as described in the last paragraph can also be found there (vanished.zip) ======================================================================= ======================================================================= If you're ready to create that "Great New Game", you might want to think about GRAPHICS TOOLS. It has everything you need! And, if you still haven't acquired all three PowerBASIC Compilers, now might be a good time to look a bit further. Pricing remains unchanged at the most competitive levels in our industry. PB/CC is our Console Compiler -- with a text mode interface to 32-bit Windows. PB 7 for Windows is oriented towards a GUI (graphical user interface) for a typical Windows "look and feel". With all of the new extensions, you won't believe how easy it is to build real GUI programs! PB/Forms is our state-of-the-art visual designer. It works with PowerBASIC 7 to build GUIs almost as fast as you can imagine them. More information? Sure, it's simple. Just click to go to each or all of the PowerBASIC product pages... PB/CC 3.0: http://www.powerbasic.com/products/pbcc/ PB/WINDOWS 7.0: http://www.powerbasic.com/products/pbdll32/ PowerBASIC Forms1.5: http://www.powerbasic.com/products/pbforms/ PowerTREE: http://www.powerbasic.com/products/powertree/ Graphics Tools: http://www.powerbasic.com/products/graftool/ SQL Tools: http://www.powerbasic.com/products/sqltools/ Console Tools: http://www.powerbasic.com/products/contools/ PB/WIN 7.0 is attractively priced at $199.00, while PB/CC 3.0 is just $169.00. Upgrades from the prior versions are just $99 and $89. PowerBASIC Forms is priced at $99, and upgrades from 1.0 are just $39. Graphics Tools Standard and Pro are $69.95 and $139.95. You can order with ease by just replying to this e-mail. You can call us at (800)780-7707 or (941)408-8700, fax us at (941)408-8820, place an electronic order on our web site (http://www.powerbasic.com), or even mail it in. But no matter the method you choose, please do it today and do it with confidence. Every product PowerBASIC ships for physical delivery is offered with a money-back guarantee for 30 days from the transaction date. Regards, Bob Zale, President PowerBASIC Inc. =================================================================== PowerBASIC Price List ------------------------------------------------------------------- PB/CC Console Compiler 3.0 - Full Product $169.00 PB/CC Console Compiler 3.0 - Upgrade from vs 2 89.00 PB/CC Console Compiler 3.0 - Upgrade from vs 1 119.00 Add Printed Documentation 39.00 ------------------------------------------------------------------- PowerBASIC for Windows 7.0 (GUI) - Full Product $199.00 PowerBASIC for Windows 7.0 - Upgrade from ver 6 99.00 PowerBASIC for Windows 7.0 - Upgrade from prior versions 129.00 Add Printed Documentation 39.00 PowerBASIC Forms Visual Design Tool for PB/Win 7 99.00 PowerBASIC Forms Visual Design Tool - Upgrade from 1.0 39.00 ------------------------------------------------------------------- PowerBASIC for DOS 3.5 - Full Product $99.00 PowerBASIC for DOS 3.5 - Upgrade from prior versions 49.00 Add Printed Documentation (2 book set) 29.00 ------------------------------------------------------------------- PowerTree BTree Manager for DOS and Windows $99.00 PB/Vision for DOS 20.00 PB/Xtra III for DOS and Windows 49.00 ------------------------------------------------------------------- Backup CD for any current PowerBASIC product $15.00 ------------------------------------------------------------------- Graphics Tools Standard ver 2 $69.95 Graphics Tools Professional ver 2 139.95 Console Tools Standard 49.95 Console Tools Professional 99.95 SQL Tools Standard Version 99.95 SQL Tools Professional Version 199.95 ------------------------------------------------------------------- Shipping/Handling costs: Software & Each Any Software 1 or 2 books Addl Book E-mail $6 N/A N/A UPS Ground/Mail US $10 $10 $6 Fedex 2-day US $16 $16 $6 Fedex 1-day US $28 $28 $6 Air Mail Canada/Mex $12 $22 $6 Air Mail Intl $16 $28 $6 Fedex Intl $34 $44 $6 ------------------------------------------------------------------- Order online at https://www.powerbasic.com/shop/ (secure server) or just send an e-mail with all pertinent information to sales@powerbasic.com and we'll take it from there! ------------------------------------------------------------------- Most PowerBASIC products (those without printed books) can now be delivered by electronic mail. No wait for a package to arrive... No high shipping costs... For just $6 per order, no matter how many products, we'll deliver directly to your computer. ==================================================================== Is your PowerBASIC Gazette Electronic Edition subscription coming to you at home or work? If you don't want to miss a single issue, why not subscribe from both e-mail addresses? Send your subscription request to email@powerbasic.com and please include your name and all e-mail addresses you'd like to add as well as your Zip or Postal Code. If you know someone else who would enjoy this newsletter please forward a copy to them so they can subscribe. ==================================================================== All contents Copyright (c) 2004 PowerBASIC Inc All Rights Reserved. PowerBASIC, PB/CC, PB/DLL, PB/Win, PowerTREE, and PowerBASIC Forms are trademarks of PowerBASIC Inc. Other names are trademarks or registered trademarks of their respective owners. ==================================================================== PowerBASIC Gazette - Electronic Edition Volume 1 - Issue 43 PowerBASIC, Inc. (800) 780-7707 Sales 1978 S. Tamiami Trail (941) 408-8700 Voice Venice, FL 34293 (941) 408-8820 Fax Visit us on the World Wide Web at http://www.powerbasic.com Email PowerBASIC Sales: sales@powerbasic.com This newsletter is only sent to e-mail addresses in our subscription list. If you have received this newsletter by mistake or no longer wish to receive it, please send a simple unsubscribe request to gazette@powerbasic.com with your name and zip/postal code. ====================================================================