Link Bar

Home | Games | Programming | Tutorials | Donate | Legal (These are mostly empty right now. Placeholders!)

warning code

This website contains adult content.

Tuesday, March 13, 2012

Day 22: "Hula" Open-Source Beta!

I got the "help" button working.  Turns out, back when I had thrown a "}" in at the end (because one was missing), I should have put it before the Help subroutine, because that's where it was missing from.  But I put it in after the Help subroutine, which subordinated it to the Inventory subroutine.  Dammit.

I don't want to admit how long it took me to figure that out.

I also think I've figured out what's causing playerLevel to start out at minus two billion, even though I know by math that it's supposed to start out at zero.  See, the exact player level on a new game is -2,147,483,648.  Recognize that number?  Yup, it's -231, the lowest number that can be displayed in 32-bit number-crunching.  I wanted "XP to next level" to always be twice what it was the last level - which is given by the function:
[LEVEL] = log2(([XP] + 1) / 2) +1
At zero XP, then, you're level zero, because log2 of 1/2 is -1 (and then add one to make it zero).  Take one action, and BAM, you're level one.  Two more actions and you're level two, and so on and so forth.  For some reason, though - probably because of how the logarithm function works under the hood - it's making it (for all intents and purposes) negative infinity.  This could be caused by the fact that I'm calculating the binary logarithm as "log2n = log10n / log102," which is mathematically correct but might be causing the 'puter to throw a fit.  Hmm.

Anyway, that's a headache for another day.  Here's the Hula beta, source code below the jump.  Also, I learned how to make the binary logarithm function here on Stack Overflow, since Microsoft decided to excise it from cmath.  Because who would ever want to take a binary logarithm of something?  Huge dorks and lesser dweebs1, that's who.

Notes:
1.  I swear by the stars that I got this from Strong Bad, but I can't find it right now.

HULA:  Hoop-Jumping Revolved
Source code


stdafx.h:

#pragma once
#include <SDKDDKVer.h>
#include <stdio.h>
#include <tchar.h>



Hula_main.cpp:

#include "Hula_Header.h" /* currently empty */
#include "stdafx.h"
#include <string>
#include <iostream>
#include <stdio.h>
#include <stdlib.h>
#include <cmath>


using namespace std;


// To get log(2)n...  
double Log2( double n )  
{  
    // compute log(10)n/log(10)2 (use const b/c windows complains w/2 logs...)  
    return ((log( n )) / (log ( 2. )));  
}


// CHARACTER INITIALIZATIONS


int playerActionCount = 0;
int playerAttackCount = 0;
int playerStealthCount = 0;
int playerCoverCount = 0;
int playerHealth = 12;
int playerHunger = 0;
int playerLocation = 4;
string speechDivider[] = {"~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"};


// GAME WORLD:
// ZONE NAMES:
string zoneName[] = {"the Column of Winter", "the Rolling Plains", "the Dense Forest", "the Craggy Mountains", "the Inner Hoop"};


// PLACE NAMES:
string placeNameCOW[] = {"Boarding Platform", "Bridge", "Pod Bay", "Crew Quarters", "Cryo Deck", "Armory", "Airlock"};
string placeNameTRP[] = {"the outskirts", "the edge", "the middle", "the middle", "the middle", "the edge", "the outskirts"};
string placeNameTDF[] = {"the outskirts", "the edge", "the middle", "the middle", "the middle", "the edge", "the outskirts"};
string placeNameTCM[] = {"the outskirts", "the edge", "the middle", "the middle", "the middle", "the edge", "the outskirts"};
string placeNameTIH[] = {"the outskirts", "the edge", "the middle", "the middle", "the middle", "the edge", "the outskirts"};


//FULL PLACE TITLE:
//described in GAME WORLD DESCRIPTION


//NPC NAMES:
string npcName[] = {"Catana", "Tiny Kitten", "Little Cat", "Maine Coon", "Tiger", "Frud", "CoW Drop"};


//INVENTORY ITEMS:
string itemName[] = {"Nunchaku", "Pistol", "Rifle", "Water Pistol", "Water Rifle", "Bullets", "Fish"};


//STARTING INVENTORY:
int playerBullets = 0;
int playerFishCount = 0;
bool inCover = false;
bool havePistol = false;
bool equipPistol = false;
bool haveRifle = false;
bool equipRifle = false;
bool haveWaterPistol = false;
bool equipWaterPistol = false;
bool haveWaterRifle = false;
bool equipWaterRifle = false;
bool haveNunchaku = true;
bool equipNunchaku = false;
bool haveCatana = true;
bool haveJanitor = false;
bool examinedOnce = false;
bool examinedTwice = false;
bool examinedThrice = false;


// PLAYER DEATH:
bool playerDeath = false;


//MAIN FUNCTION!
int _tmain(int argc, _TCHAR* argv[])
{
//PRELIMINARIES:
cout<<"One Man Show"<<endl;
cout<<endl;
cout<<endl;
/* This "title screen" may not show up properly because of the blogger.  Don't worry about it. */
cout<<"H   H  U   U  L       A"<<endl;
cout<<"H   H  U   U  L      A A"<<endl;
cout<<"H   H  U   U  L     A   A"<<endl;
cout<<"HHHHH  U   U  L  ((_A___A_))"<<endl;
cout<<"H   H  U   U  L    _A___A_/"<<endl;
cout<<"H   H  U   U  L     A   A"<<endl;
cout<<"H   H   UUU   LLLL  A   A"<<endl;
cout<<"---------------------------"<<endl;
cout<<"   HOOP-JUMPING REVOLVED"<<endl;
cout<<endl;
cout<<endl;
cout<<"Press 'Ender' to begin a game."<<endl;
char playerAction[10];
cin.getline(playerAction,10);


//PLAYER NAMING
cout<<endl;
cout<<"What is your cat's name?"<<endl;
char playerName[100];
cin.getline(playerName,100);
cout<<"Your cat has been promoted to Sergeant " <<playerName <<".  Aren't you proud?\n(Press 'Ender' to continue.)" <<endl;
cin.getline(playerAction,10);
cout<<"Our story begins on a dark and stormy night in space.\nIt's always dark and stormy in space, what with the darkness\nand all the radiation and whatnot.\n(Press 'Ender' to continue.)"<<endl;
cin.getline(playerAction,10);
cout<< speechDivider[0] <<endl;
cout<<"FEMALE VOICE:  Sergeant?"<<endl;
cout<< speechDivider[0] <<endl;
cin.getline(playerAction,10);
cout<< speechDivider[0] <<endl;
cout<<"FEMALE VOICE:  Sergeant " <<playerName <<"?"<<endl;
cout<< speechDivider[0] <<endl;
cin.getline(playerAction,10);
cout<< speechDivider[0] <<endl;
cout<<"FEMALE VOICE:  Sarge!  You need to wake up!"<<endl;
cout<< speechDivider[0] <<endl;


//GAME LOOP!
while (playerDeath == false) {

//GAME GOES HERE!

//CALCULATE PLAYER STATS
int playerLevel = Log2((playerActionCount + 1 )/2)+1;
int playerAttackLevel = Log2((playerAttackCount + 1)/2)+1;
int playerStealthLevel = Log2((playerStealthCount + 1)/2)+1;
int playerCoverLevel = Log2((playerCoverCount + 1)/2)+1;
int playerMaxHealth = 12 + (playerLevel * 4);

//GAME WORLD DESCRIPTION
cout<<"You are at the ";
if (playerLocation >= 28) {
cout<<placeNameTIH[playerLocation - 28];
}
else if (playerLocation >= 21) {
cout<<placeNameTCM[playerLocation - 21];
}
else if (playerLocation >= 14) {
cout<<placeNameTDF[playerLocation - 14];
}
else if (playerLocation >= 7) {
cout<<placeNameTDF[playerLocation - 7];
}
else {
cout<<placeNameCOW[playerLocation];
}
cout<<" of " <<zoneName[playerLocation/7] <<"."<<endl;


//PLAYER DESCRIPTION
cout<<"You have " <<playerHealth <<" HP and are level " <<playerLevel <<"."<<endl;

//OFFER PLAYER ACTION
cout<<"What do you do?  (Ender 'H' to access Help screen.)"<<endl;
cin.getline(playerAction,10);
cout<<"x-x-x-x-x-x-x-x-x-x-x-x-x-x-x-x-x-x-x-x"<<endl;

//RESOLVE PLAYER ACTION


//QUEST ACTION SUBROUTINE
if (playerAction[0]=='q') {
cout<<"There are no quest actions to be performed here."<<endl;
}


//TRAVEL SUBROUTINE
if (playerAction[0]=='w') {
cout<<"You advance through " <<zoneName[playerLocation/7] <<"."<<endl;
playerLocation = playerLocation +1;
playerActionCount = playerActionCount +1;
inCover = false;
}


//RETREAT SUBROUTINE (R)
if (playerAction[0]=='r') {
cout<<"You retreat back through " <<zoneName[playerLocation/7] <<"."<<endl;
playerLocation = playerLocation -1;
playerActionCount = playerActionCount +1;
inCover = false;
}


//EAT FISH SUBROUTINE (E)
if (playerAction[0]=='e') {
if (playerFishCount==0) {
cout<<"You have no fish to eat."<<endl;
}
else {
cout<<"You eat a fish and restore your health."<<endl;
playerFishCount = playerFishCount -1;
playerHealth = playerMaxHealth;
playerActionCount = playerActionCount + 1;
playerHunger = 0;
}
}


//ATTACK SUBROUTINE (A)
if (playerAction[0]=='a') {
cout<<"There is nobody to attack here."<<endl;
}


//STEALTH SUBROUTINE (S)
if (playerAction[0]=='s') {
cout<<"There is nobody to sneak past here."<<endl;
}


//DEVICE SUBROUTINE (D)
if (playerAction[0]=='d') {
cout<<"You consult your device!"<<endl;
}


//MINE FOR FISH SUBROUTINE (F)
//ADD FUNCTIONALITY FOR WHEN A LOCATION HAS ALREADY BEEN MINED!
if (playerAction[0]=='f') {
if (playerLocation<=6) {
cout<<"You can't mine for fish inside a spaceship, stupid."<<endl;
}
cout<<"You sniff around and find a fish to dig up."<<endl;
playerFishCount = playerFishCount +1;
playerHunger = playerHunger +1;
playerActionCount = playerActionCount +1;
}


//COVER SUBROUTINE (C)
if (playerAction[0]=='c') {
if (inCover==true) {
cout<<"You're already behind cover."<<endl;
}
if (playerLocation/7==1) {
cout<<"You can't find any cover in " <<zoneName[playerLocation/7] <<"."<<endl;
}
cout<<"You take cover behind ";
if (playerLocation/7==0) {
cout<<"a doorway";
}
if (playerLocation/7==2) {
cout<<"a tree";
}
if (playerLocation/7==3) {
cout<<"a rock";
}
if (playerLocation/7==4) {
cout<<"a corner";
}
cout<<"."<<endl;
playerHunger = playerHunger +1;
playerActionCount = playerActionCount +1;
playerCoverCount = playerCoverCount +1;
inCover = true;
}
//EXAMINE SUBROUTINE (X)
if (playerAction[0]=='x') {
cout<<"You spend a moment taking in your surroundings."<<endl;
if (examinedOnce==true) {
if (examinedTwice==true) {
if (examinedThrice==true) {
cout<<"You have seen all that there is to see.\nDo not gaze too harshly, or you shall see no more."<<endl;
}
else {
cout<<"You perceive the ultimate nature of reality, but cannot put it into words."<<endl;
examinedThrice=true;
}
}
else {
cout<<"You begin to see the connections among all things, and you feel at one with the world."<<endl;
examinedTwice=true;
}
}
if (examinedOnce==false) {
cout<<"Looking closely at the world, you begin to see the beauty in all things."<<endl;
examinedOnce=true;
}
}
//TAKE ITEM SUBROUTINE (Z)
if (playerAction[0]=='z') {
cout<<"There are no items here for you to take."<<endl;
}


//INVENTORY SUBROUTINE (I)
if (playerAction[0]=='i') {
cout<<"You have ";
if (havePistol==true) {
cout<<"a " <<itemName[1] <<", ";
} else {cout<<"";}
if (haveRifle==true) {
cout<<"a " <<itemName[2] <<", ";
} else {cout<<"";}
if (haveWaterPistol==true) {
cout<<"a " <<itemName[3] <<", ";
} else {cout<<"";}
if (haveWaterRifle==true) {
cout<<"a " <<itemName[4] <<", ";
} else {cout<<"";}
cout<<endl <<playerBullets <<" bullets, " <<playerFishCount <<" fish, and a pair of nunchaku."<<endl;
cout<<"To equip an item, enter 1 for your Pistol, 2 for Rifle,"<<endl;
cout<<"3 for Water Pistol, 4 for Water Rifle, or 5 for Nunchaku."<<endl;
char equipItem[10];
cin.getline(equipItem,10);
if (equipItem[0]==1) {
if (havePistol = true) {
equipPistol = true;
equipRifle = false;
equipWaterPistol = false;
equipWaterRifle = false;
equipNunchaku = false;
} else {cout<<"You have no pistol to equip."<<endl;}
}
if (equipItem[0]==2) {
if (haveRifle = true) {
equipPistol = false;
equipRifle = true;
equipWaterPistol = false;
equipWaterRifle = false;
equipNunchaku = false;
} else {cout<<"You have no rifle to equip."<<endl;}
}
if (equipItem[0]==3) {
if (haveWaterPistol = true) {
equipPistol = false;
equipRifle = false;
equipWaterPistol = true;
equipWaterRifle = false;
equipNunchaku = false;
} else {cout<<"You have no water pistol to equip."<<endl;}
}
if (equipItem[0]==4) {
if (haveWaterRifle = true) {
equipPistol = false;
equipRifle = false;
equipWaterPistol = false;
equipWaterRifle = true;
equipNunchaku = false;
} else {cout<<"You have no water rifle to equip."<<endl;}
}
if (equipItem[0]==5) {
if (haveNunchaku = true) {
equipPistol = false;
equipRifle = false;
equipWaterPistol = false;
equipWaterRifle = false;
equipNunchaku = true;
} else {cout<<"You have no nunchaku to equip.  How did that happen?"<<endl;}
} else {cout<<"You can't equip that."<<endl;}
}


//HELP SUBROUTINE (H)
//DOES NOT WORK?!
if (playerAction[0]=='h') {
cout<<"You are able to take the following actions:"<<endl;
cout<<"W - Move forward through the world,"<<endl;
cout<<"R - Move backward (retreat) through the world."<<endl;
cout<<"Q - Perform Quest action.  E - Eat fish."<<endl;
cout<<"A - Attack enemies.  S - Sneak past enemies."<<endl;
cout<<"D - Consult Device AI.  F - Mine for fish."<<endl;
cout<<"C - Take cover. X - Examine surroundings."<<endl;
cout<<"Z - Take item.  I - Inventory."<<endl;
}

//DEATH CONDITION:
if (playerHealth<=0) {
playerDeath = true;
}


//END OF TURN DIVIDER:
cout<<"x-x-x-x-x-x-x-x-x-x-x-x-x-x-x-x-x-x-x-x"<<endl;
}

cout<<"The game is now over.  Press 'Ender' to quit."<<endl;
//GAME ENDS
return 0;
}

2 comments:

  1. inside of Log2:

    if (n == 0) { return 0; }

    ReplyDelete
  2. ::facepalm:: Of course. How silly of me not to have thought of that! Thank you for reminding me once again of Alexander the Great.

    By the way, it was if(n==1/2){return -1;}. But the logical workaround was what I really needed, and you provided. Thanks again!

    ReplyDelete