Goofans Game Discussion

809 replies [Last post]
Joined: 07/08/2011

Why an int? Why not a boolean?

The console didn't get anywhere, really. Right now I'm really just focusing on reading map files and displaying images accordingly.

EDIT: I may just have a little textbox for inputting commands like how Simcity does it.

Joined: 09/01/2009

I'm saying for more than one flag, an int is far better than multiple booleans, since you can store up to 32 flags per a 32-bit int using bitfields. If you're using booleans, storing 32 flags would be 256 bits (32 * 8-bit booleans, as booleans are internally represented by most compilers as chars). Besides which, it's a gazillion times less confusing to use one bitfield with a few macros than a bunch of different booleans. Believe me, I've figured this out the hard way.

So, for example, rather than using

bool bSpawnEnemies;
bool bInvincible;
bool bUnlimitedAmmo;
bool bUnlimitedGold;
 
bUnlimitedAmmo = true;

etc., you'd have
#define SPAWNENEMIES  0x01
#define INVINCIBLE    0x02
#define UNLIMITEDAMMO 0x04
#define UNLIMITEDGOLD 0x08
 
unsigned int     iCheatBitfield;
 
iCheatBitfield |= UNLIMITEDAMMO;

If you have more than 4 flags (that make sense being grouped together, of course), you'll just be using a single bit for each additional flag up to 32, instead of using 8 bits per new boolean. Besides which, it's a lot less confusing to use a single int rather than having a bunch of random booleans all over the place. Then, you can

if(iCheatBitfield & INVINCIBLE)

instead of
if(bInvincible)

Or even make a handy-dandy macro to help you out. Like:
#define TESTBOOL(x) (iCheatBitfield & x)

so you can:
if(TESTBOOL(INVINCIBLE))

C-style programming to the rescue. Laughing out loud

Joined: 07/08/2011

SCREW THAT! I'm going boolean all the way, baby! Laughing out loud

Seriously, I may or may not switch. Those small byte-differences aren't enough to make me want to retype code for a whole 10 minutes! I mean, that's enough time for me to eat a block of cheese!

On another note, any coders who want to see the current (messy) code I'm building from, it can be found here. It's a Code::Blocks project with all 3rd party libraries included with the project file so it should run without any hassle. I know it isn't great, this was my last restart, but it shows what I've been doing on the trip to L.A. today. I was coding the whole trip, there and back. I fear I may getting carpal tunnel.

In terms of headers, the files are:
definitions.h: defining custom core functions, values, surface, etc.
img.h: drawing functions
xml.h: map-reading/xml-reading functions
gameloop.h: has the gameloop, as you may expect. It also contains the calls to the drawing functions required to display current anything.

Developer keys:
F3: Toggle Developer Mode (text display on top-left corner)
--I: Toggle Infinites State (all values kept at 9999)
--N: Toggle Noclip State (will override gravity once I have it implemented :3)

The zip also includes the current .exe and map xmls, so if anybody wants to go in there and make their own map (currently only has "image" elements) feel free to do so. Also, "depth" attribute for the images has to be an integer from 0 to 9999 (10000 in total). Any other value will cause a crash, I think.

Joined: 09/01/2009

For different things, boolean may or may not be easier. It depends. If you're using just one bool for a few things here and there, it's perfectly fine. But a bitfield is better than a ton of bools that are used for similar things. So my example was rather than having a ton of bools for cheat mode, a single bitfield would be easier to keep track of everything.

Also, btw, small differences in bits can be huge if you're porting the game to a device that has a smaller stack. Clever optimization can help a game run a lot better. Wink

But you're right. Probably a bit (haha, pun) too early to worry about this sort of thing. Keep it in mind, though, in case you ever have to program something small, like an embedded system.

*looks at code*
1. itoa() is a nonstandard C function (i.e. only a few compilers on a few platforms like it), and it's totally pointless to use it with C++ strings anyway. So,

EDIT: See below

Joined: 07/08/2011

Oh, I didn't know that would work. A friend suggested string [blah] += player.GP; instead of append, but it didn't work. I didn't know you could treat integers like that.

Joined: 09/01/2009

That's the whole point of using C++ rather than C strings, so yep. Tongue

EDIT: Nvm, something about that isn't working. Brb...

EDIT2: Ok, scratch what I said before; didn't quite work. This does:

Replace

char tempchar[32];
string hpText = itoa( player.HP, tempchar, 10 );
string mpText = itoa( player.MP, tempchar, 10 );
string gpText = itoa( player.GP, tempchar, 10 );
stateText = "HP: ";
stateText.append( hpText );
stateText.append( ", MP: " );
stateText.append( mpText );
stateText.append( ", GP: " );
stateText.append( gpText );

with
ostringstream oss;
oss << "HP: " << player.HP << ", MP: " << player.MP << ", GP: " << player.GP;
stateText = oss.str();

and #include <sstream> at the top of the file. Simpler, eh? And cross-platform too. Smile C++ is your friend.

By the way, function implementations shouldn't be in header files unless they're inline. The reason for this is if you include the header file in more than one implementation (i.e. .cpp) file, you'll get linker errors.

EDIT3: Ok, I'm done Linux build: Here (64-bit)

Basically, the standard repo libs for tinyxml are outdated (it happens), so I included the latest tinyxml in the program (I could compile it into a statically or dynamically linked library, but I felt lazy), and fixed a few things in the linker settings accordingly (removed -lTinyXml, and added `sdl-config --libs` for linker errors). Fixed what I pointed out above (as itoa() doesn't work on Linux's GCC), and I think that's about it. It was a fairly simple port, so kudos so far, Red. Laughing out loud

This version may or may not work right on Windows anymore; it's tough to say. If it doesn't, then just change the code I showed you above, and don't worry about tinyxml or the linker settings. Keep up the good work! And take care of your wrist; carpal tunnel isn't fun. I've had it before.

Joined: 12/23/2010

A lot of stuff going on. That's what happens when I miss a day...

Anyway, about the console, I think that Courier Bold or Courier New Bold is good. But no italics.
And maybe it should pause the game and fill up the top half of the screen. It's clear, and easy to use.

Joined: 08/06/2010

I've been writing libraries for all the thngs that should be implemented in cstdlib but aren't. One of those defines ctos, itos, and dtos functions for conversions.

I just finished one to implement a Typestream, just like an Ostream but it types it out one character at a time. Useless, but fun and a cool effect. Smile

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 09/01/2009

I don't see why anyone would want something like itoa() anyway, since you can just use sprintf(). But that's logic fer ya.

Joined: 08/06/2010

sprintf()? What's wrong with basic stringstreams?

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 09/01/2009

I meant in C.

Joined: 08/06/2010

True, then.

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 07/08/2011

Okay, implementing. Thanks for the Linux build. I'm not going to use it, because I'm on Windows, but I'll replace some of what you're suggesting.

By the way, what do you think overall? The reason I keep restarting is because the code looks ugly, and my old code looks quite so. Basically, it had no comments whatsoever and useless Windows-only functions.

The reason I was including windows.h was only for the Beep(,) function. I just wanted to see how far my code would get before it crashed. (yes, I realize a debugger can do this, but I like beeps more :3)

Joined: 08/06/2010

cout << '\a'

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 07/08/2011

Be quiet...

Joined: 08/06/2010

Or
#define beep '\a'

cout << beep

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 07/08/2011

'\a' is shorter.

Joined: 08/06/2010

strlen("\'\a\'") = 4
strlen("beep") = 4
4 == 4

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 07/08/2011

"\?

Joined: 08/06/2010

'\a' ->
'\\a' ->
\'\\a\' Still four characters, \' \\ a \'

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 07/08/2011

No, I thought you were making "\ your first escape code. I was wrong.

Joined: 08/06/2010

Oh. I see.

Back on topic now...

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 09/01/2009

Ooh, ooh! Write some low-level DOS routines that control the PC speaker directly. That way you can make all kinds of sounds. Laughing out loud

That's what a lot of old 90's games did, anyhow. I doubt it works at all on modern sound cards, though...

Code structure is really hard for me, too (actually, it's hard for everybody! Even the epic geeks who work on really high-end projects like the Linux kernel have difficulty making their code work well as new features are added). I think some people extrapolate their code into a zillion classes for this very reason. Breaking stuff up into functions helps, breaking it into different classes where applicable helps more, and breaking it up into aptly-named files helps even more. Try to think of what you'll be adding where to do what, and split stuff up now before it's all so tied together that it's nearly impossible to split stuff up. I wish there was some magic formula for this, but there isn't. Comments help a lot, too.

The good news is that if your code ends up atrocious, there's no reason to panic. A lot of indie games have horrible code. Aquaria, from what I've heard, is a complete and utter mess, with thousands of lines of code per file and terrible organization. A few quirky bugs because of it, too. And Minecraft's code is so awful that for everything they add, some new, completely unrelated, bug crops up for no reason at all. Fixing bugs as they crop up (or later) is fun, too, and I can help. It takes practice to create non-messy code, really, and nobody's perfect at it yet (anybody who's seen a BSOD for seemingly no reason knows that).

I didn't look at your organization a whole lot (I was too busy fixing bugs to get it to compile on my Linux machine), but a few things I did notice:

-A small main() function. That's good. You're on the right track with that.
-Generically-named files. I tend to do this some, too; name something misc.cpp and throw a bunch of random stuff in there. It's better to have a naming scheme that tells you what the functions in there do (like tilemap.cpp for reading in and generating a map from a file, or drawingcycle.cpp for handling all the drawing for one cycle of the game).
-Functions in header files. Not good unless they're small and inline.

I didn't go over it thoroughly, though.

Joined: 07/08/2011

System sounds is exactly how .org sound files were played in Cave Story. Wink Why do you think it took him 5 years to finish? That part alone must have eaten up a few months at the least. The thing is, with modern games to compare with, nobody but us nerds will settle for a series of beeps. We should have a modern format, like .ogg, and with a good composer.

I've looked at it, and yes, Aquaria's code is many files with loads of random code. I can't even find the main().

Yeah, thanks. I think this try is a keeper. Smile

Joined: 08/06/2010

What? Most people like sounds other than the system ding? Shock

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 09/01/2009

What's crazy is games where people used system dings to make speech synthesizers. Like, it could actually sound kind of like someone talking. It's amazing that they actually took the time to do that, and it actually turned out sounding a lot like speech!

Joined: 08/06/2010

Wow.

Let's do that for one of the monster races. Totally.

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 07/08/2011

Epic. I totally agree, but I'm not doing that.

EDIT: Oh and I forgot to mention I'm not going to use more than one .cpp file, or at least I don't plan to.

Joined: 08/06/2010

Why not? It makes the code much cleaner, and you can use a MakeFile to link them automatically.

Another Planet finally has an official release! Download chapters 1 through 3 here! Thank you for waiting so long while I kept starting over.

Joined: 09/01/2009

^^

Deciding to limit yourself to one file is an insanely bad idea, since it gets ridiculously difficult to find anything when it has much more than a thousand lines of code, and believe me, you'll end up with several thousand. Not to mention compile times and such.