Sign in to follow this  
GraySnakeGenocide

Beginner troubles

Recommended Posts

Ok so, here I am, focusing on learning C#. Following a game making tutorial in a book.

Problem is, I come across code with dozens of numbers, x's, y's, etc. How am I supposed to remember/know all of this? I for the life of me, can barely understand it, seeing as it's being thrown at me all at once. And secondly, how in the hell am I supposed to remember everything needed to fully put the game together when it comes time to try remaking the game without looking at the book?

My memory sucks, everything I read tends to go in one ear and out the other.
I have no idea how I'm going to get any of this to stick :(.

Share this post


Link to post
Share on other sites
Quote:
Original post by GraySnakeGenocide
Ok so, here I am, focusing on learning C#. Following a game making tutorial in a book.

Problem is, I come across code with dozens of numbers, x's, y's, etc. How am I supposed to remember/know all of this? I for the life of me, can barely understand it, seeing as it's being thrown at me all at once. And secondly, how in the hell am I supposed to remember everything needed to fully put the game together when it comes time to try remaking the game without looking at the book?

My memory sucks, everything I read tends to go in one ear and out the other.
I have no idea how I'm going to get any of this to stick :(.


a) game design document
b) source code comments
c) well named variables (with good naming convention)
d) there's no secret, you don't remember everything. it's like driving, you can't jot down everything from A to Z from memory, but as you drive, you will realize that scenery and sign will help you arrive at your destination.

your current self and your past self can be treated as different team member in a large company, where you will do things using their code without even looking into the code, only the function names - and trust the rest.

Share this post


Link to post
Share on other sites
I've been programming for well over a decade. I constantly look at manuals. Sometimes I review them in more detail, including methods I've used a hundred times, to make sure I'm only invoking defined behavior.

A lot of programming techniques are focused around reducing complexity of what you have to think about.

This is why there are "private" members, for example. When I use a JButton class, I don't want to have in my head how the guts work or how it renders. I just want to use a few interfaces; setText, addActionListener, and use another kit to set it into a panel. All the internal machinations are hidden from me behind a carefully defined interface.

This is called "information hiding".

After all that, there's still a lot of complexiy. Having a brain for that is part of being a programmer.

Quote:
well named variables (with good naming convention)


QFT. In the PHP language, the naming is very haphazard, so if you know you want to call "string split", you don't know of it's going to be splitstring, spltstr, split_string or split_str. It might as well be pictograms. If you know that "split string" will be "splitString" because you always name things with the same convention, you avoid a lot of pain.

Share this post


Link to post
Share on other sites
Writing down when needs to be implemented, and doing each method individually helped for the smaller project, but this next project has like, a million int x's, a million int y's, Vectors, etc. All of it is making my head spin >_<.

I'm going to try the one method at a time bit once I finish the game via following the book, and hopefully i'll do it enough times where I will remember each method the I previously forgot, if that makes sense >_<.

Share this post


Link to post
Share on other sites
My issue is, I am following a book, and it's having me do a FloodControl game.

There are 3 classes:

Game1
using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.GamerServices;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Media;

namespace Flood_Control
{
/// <summary>
/// This is the main type for your game
/// </summary>
public class Game1 : Microsoft.Xna.Framework.Game
{
GraphicsDeviceManager graphics;
SpriteBatch spriteBatch;

Texture2D playingPieces;
Texture2D backgroundScreen;
Texture2D titleScreen;

GameBoard gameBoard;

Vector2 gameBoardDisplayOrigin = new Vector2(70, 89);

int playerScore = 0;

enum GameStates { TitleScreen, Playing };
GameStates gameState = GameStates.TitleScreen;

Rectangle EmptyPiece = new Rectangle(1, 247, 40, 40);

const float MinTimeSinceLastInput = 0.25f;
float timeSinceLastInput = 0.0f;


public Game1()
{
graphics = new GraphicsDeviceManager(this);
Content.RootDirectory = "Content";
}

/// <summary>
/// Allows the game to perform any initialization it needs to before starting to run.
/// This is where it can query for any required services and load any non-graphic
/// related content. Calling base.Initialize will enumerate through any components
/// and initialize them as well.
/// </summary>
protected override void Initialize()
{
// TODO: Add your initialization logic here
this.IsMouseVisible = true;
graphics.PreferredBackBufferWidth = 800;
graphics.PreferredBackBufferHeight = 600;
graphics.ApplyChanges();
gameBoard = new GameBoard();
base.Initialize();
}

/// <summary>
/// LoadContent will be called once per game and is the place to load
/// all of your content.
/// </summary>
protected override void LoadContent()
{
// Create a new SpriteBatch, which can be used to draw textures.
spriteBatch = new SpriteBatch(GraphicsDevice);

playingPieces = Content.Load<Texture2D>(@"Textures\Tile_Sheet");
backgroundScreen = Content.Load<Texture2D>(@"Textures\Background");
titleScreen = Content.Load<Texture2D>(@"Textures\TitleScreen");

// TODO: use this.Content to load your game content here
}

/// <summary>
/// UnloadContent will be called once per game and is the place to unload
/// all content.
/// </summary>
protected override void UnloadContent()
{
// TODO: Unload any non ContentManager content here
}

private int DetermineScore(int SquareCount)
{
return (int)((Math.Pow((SquareCount / 5), 2) + SquareCount) * 10);
}

private void CheckScoringChain(List<Vector2> WaterChain)
{

if (WaterChain.Count > 0)
{
Vector2 LastPipe = WaterChain[WaterChain.Count - 1];

if (LastPipe.X == GameBoard.GameBoardWidth - 1)
{
if (gameBoard.HasConnector(
(int)LastPipe.X, (int)LastPipe.Y, "Right"))
{
playerScore += DetermineScore(WaterChain.Count);

foreach (Vector2 ScoringSquare in WaterChain)
{
gameBoard.SetSquare((int)ScoringSquare.X,
(int)ScoringSquare.Y, "Empty");
}
}
}
}
}

private void HandleMouseInput(MouseState mouseState)
{

int x = ((mouseState.X -
(int)gameBoardDisplayOrigin.X) / GamePiece.PieceWidth);

int y = ((mouseState.Y -
(int)gameBoardDisplayOrigin.Y) / GamePiece.PieceHeight);

if ((x >= 0) && (x < GameBoard.GameBoardWidth) &&
(y >= 0) && (y < GameBoard.GameBoardHeight))
{
if (mouseState.LeftButton == ButtonState.Pressed)
{
gameBoard.RotatePiece(x, y, false);
timeSinceLastInput = 0.0f;
}

if (mouseState.RightButton == ButtonState.Pressed)
{
gameBoard.RotatePiece(x, y, true);
timeSinceLastInput = 0.0f;
}
}
}

/// <summary>
/// Allows the game to run logic such as updating the world,
/// checking for collisions, gathering input, and playing audio.
/// </summary>
/// <param name="gameTime">Provides a snapshot of timing values.</param>
protected override void Update(GameTime gameTime)
{
// Allows the game to exit
if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
this.Exit();

// TODO: Add your update logic here

switch (gameState)
{
case GameStates.TitleScreen:
if (Keyboard.GetState().IsKeyDown(Keys.Space))
{
gameBoard.ClearBoard();
gameBoard.GenerateNewPieces(false);
playerScore = 0;
gameState = GameStates.Playing;
}
break;

case GameStates.Playing:
timeSinceLastInput +=
(float)gameTime.ElapsedGameTime.TotalSeconds;

if (timeSinceLastInput >= MinTimeSinceLastInput)
{
HandleMouseInput(Mouse.GetState());
}

gameBoard.ResetWater();

for (int y = 0; y < GameBoard.GameBoardHeight; y++)
{
CheckScoringChain(gameBoard.GetWaterChain(y));
}

gameBoard.GenerateNewPieces(true);

break;
}

base.Update(gameTime);
}

/// <summary>
/// This is called when the game should draw itself.
/// </summary>
/// <param name="gameTime">Provides a snapshot of timing values.</param>
protected override void Draw(GameTime gameTime)
{
GraphicsDevice.Clear(Color.CornflowerBlue);

// TODO: Add your drawing code here

if (gameState == GameStates.TitleScreen)
{
spriteBatch.Begin();
spriteBatch.Draw(titleScreen,
new Rectangle(0, 0,
this.Window.ClientBounds.Width,
this.Window.ClientBounds.Height),
Color.White);
spriteBatch.End();
}

if (gameState == GameStates.Playing)
{
spriteBatch.Begin();

spriteBatch.Draw(backgroundScreen,
new Rectangle(0, 0,
this.Window.ClientBounds.Width,
this.Window.ClientBounds.Height),
Color.White);

for (int x = 0; x < GameBoard.GameBoardWidth; x++)
for (int y = 0; y < GameBoard.GameBoardHeight; y++)
{
int pixelX = (int)gameBoardDisplayOrigin.X +
(x * GamePiece.PieceWidth);
int pixelY = (int)gameBoardDisplayOrigin.Y +
(y * GamePiece.PieceHeight);

spriteBatch.Draw(
playingPieces,
new Rectangle(
pixelX,
pixelY,
GamePiece.PieceWidth,
GamePiece.PieceHeight),
EmptyPiece,
Color.White);

spriteBatch.Draw(
playingPieces, new Rectangle(
pixelX,
pixelY,
GamePiece.PieceWidth,
GamePiece.PieceHeight),
gameBoard.GetSourceRect(x, y),
Color.White);
}

this.Window.Title = playerScore.ToString();

spriteBatch.End();
}

base.Draw(gameTime);
}
}
}




GamePiece
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework;

namespace Flood_Control
{
class GamePiece
{
public static string[] PieceTypes =
{
"Left,Right",
"Top,Bottom",
"Left,Top",
"Top,Right",
"Right,Bottom",
"Bottom,Left",
"Empty"
};

public const int PieceHeight = 40;
public const int PieceWidth = 40;

public const int MaxPlayablePieceIndex = 5;
public const int EmptyPieceIndex = 6;

private const int textureOffsetX = 1;
private const int textureOffsetY = 1;
private const int texturePaddingX = 1;
private const int texturePaddingY = 1;

private string pieceType = "";
private string pieceSuffix = "";

public string PieceType
{
get { return pieceType; }
}

public string Suffix
{
get { return pieceSuffix; }
}

public GamePiece(string type, string suffix)
{
pieceType = type;
pieceSuffix = suffix;
}

public GamePiece(string type)
{
pieceType = type;
pieceSuffix = "";
}

public void SetPiece(string type, string suffix)
{
pieceType = type;
pieceSuffix = suffix;
}

public void SetPiece(string type)
{
SetPiece(type, "");
}

public void AddSuffix(string suffix)
{
if (!pieceSuffix.Contains(suffix))
pieceSuffix += suffix;
}

public void RemoveSuffix(string suffix)
{
pieceSuffix = pieceSuffix.Replace(suffix, "");
}

public void RotatePiece(bool Clockwise)
{
switch (pieceType)
{
case "Left,Right":
pieceType = "Top,Bottom";
break;
case "Top,Bottom":
pieceType = "Left,Right";
break;
case "Left,Top":
if (Clockwise)
pieceType = "Top,Right";
else
pieceType = "Bottom,Left";
break;
case "Top,Right":
if (Clockwise)
pieceType = "Right,Bottom";
else
pieceType = "Left,Top";
break;
case "Right,Bottom":
if (Clockwise)
pieceType = "Bottom,Left";
else
pieceType = "Top,Right";
break;
case "Bottom,Left":
if (Clockwise)
pieceType = "Left,Top";
else
pieceType = "Right,Bottom";
break;
case "Empty":
break;
}
}

public string[] GetOtherEnds(string startingEnd)
{
List<string> opposites = new List<string>();

foreach (string end in pieceType.Split(','))
{
if (end != startingEnd)
opposites.Add(end);
}
return opposites.ToArray();
}

public bool HasConnector(string direction)
{
return pieceType.Contains(direction);
}

public Rectangle GetSourceRect()
{
int x = textureOffsetX;
int y = textureOffsetY;

if (pieceSuffix.Contains("W"))
x += PieceWidth + texturePaddingX;

y += (Array.IndexOf(PieceTypes, pieceType) *
(PieceHeight + texturePaddingY));


return new Rectangle(x, y, PieceWidth, PieceHeight);
}

}
}



GameBoard
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework;

namespace Flood_Control
{
class GameBoard
{
Random rand = new Random();

public const int GameBoardWidth = 8;
public const int GameBoardHeight = 10;

private GamePiece[,] boardSquares =
new GamePiece[GameBoardWidth, GameBoardHeight];

private List<Vector2> WaterTracker = new List<Vector2>();

public GameBoard()
{
ClearBoard();
}

public void ClearBoard()
{
for (int x = 0; x < GameBoardWidth; x++)
for (int y = 0; y < GameBoardHeight; y++)
boardSquares[x, y] = new GamePiece("Empty");
}

public void RotatePiece(int x, int y, bool clockwise)
{
boardSquares[x, y].RotatePiece(clockwise);
}

public Rectangle GetSourceRect(int x, int y)
{
return boardSquares[x, y].GetSourceRect();
}

public string GetSquare(int x, int y)
{
return boardSquares[x, y].PieceType;
}

public void SetSquare(int x, int y, string pieceName)
{
boardSquares[x, y].SetPiece(pieceName);
}

public bool HasConnector(int x, int y, string direction)
{
return boardSquares[x, y].HasConnector(direction);
}

public void RandomPiece(int x, int y)
{
boardSquares[x, y].SetPiece(GamePiece.PieceTypes[rand.Next(0,
GamePiece.MaxPlayablePieceIndex + 1)]);
}

public void FillFromAbove(int x, int y)
{
int rowLookup = y - 1;

while (rowLookup >= 0)
{
if (GetSquare(x, rowLookup) != "Empty")
{
SetSquare(x, y,
GetSquare(x, rowLookup));
SetSquare(x, rowLookup, "Empty");
rowLookup = -1;
}
rowLookup--;
}
}

public void GenerateNewPieces(bool dropSquares)
{

if (dropSquares)
{
for (int x = 0; x < GameBoard.GameBoardWidth; x++)
{
for (int y = GameBoard.GameBoardHeight - 1; y >= 0; y--)
{
if (GetSquare(x, y) == "Empty")
{
FillFromAbove(x, y);
}
}
}
}

for (int y = 0; y < GameBoard.GameBoardHeight; y++)
for (int x = 0; x < GameBoard.GameBoardWidth; x++)
{
if (GetSquare(x, y) == "Empty")
{
RandomPiece(x, y);
}
}
}

public void ResetWater()
{
for (int y = 0; y < GameBoardHeight; y++)
for (int x = 0; x < GameBoardWidth; x++)
boardSquares[x, y].RemoveSuffix("W");
}

public void FillPiece(int X, int Y)
{
boardSquares[X, Y].AddSuffix("W");
}

public void PropagateWater(int x, int y, string fromDirection)
{
if ((y >= 0) && (y < GameBoardHeight) &&
(x >= 0) && (x < GameBoardWidth))
{
if (boardSquares[x, y].HasConnector(fromDirection) &&
!boardSquares[x, y].Suffix.Contains("W"))
{
FillPiece(x, y);
WaterTracker.Add(new Vector2(x, y));
foreach (string end in
boardSquares[x, y].GetOtherEnds(fromDirection))
switch (end)
{
case "Left": PropagateWater(x - 1, y, "Right");
break;
case "Right": PropagateWater(x + 1, y, "Left");
break;
case "Top": PropagateWater(x, y - 1, "Bottom");
break;
case "Bottom": PropagateWater(x, y + 1, "Top");
break;
}
}
}
}

public List<Vector2> GetWaterChain(int y)
{
WaterTracker.Clear();
PropagateWater(0, y, "Left");
return WaterTracker;
}


}
}



I have no clue how I am supposed to break all this stuff down and understand it. I have practically no clue what a Vector is, even though I looked it up on this site. I don't know how they came up with some of those numbers. I have never been good at math, so I don't know how I am supposed to manage this.
The book breaks each thing into sections, but still.

Share this post


Link to post
Share on other sites
Many of the actual numbers in there are ass-pulls. Why a game board with of 8? Why not?

It sounds to me like you don't understand what you're doing at the most basic level.

Understanding a vector is easy if you understand what an array is.

Take an array, like:

int[] myArray = new int[5];


I have an array with five slots. I can edit them.

But can't resize the array. I can't just say "add this, add that, and this" arbitrarily without writing functions like this:

int currentIndex = 0;
int[] myArray = new int[5];
public void addAnInt(int i)
{
myArray[currentIndex] = i;
currentIndex++;
}


And if I used that function (addAnInt) too many times, it'd throw an ArrayIndexOutOfBounds exception because it overflowed.

And if it was written in a lower level language like C that doesn't keep track of such things, it'd just plain blow up in my face, or worse.

So a Vector does all that for me. It handles the resizing and everything, so I can do this:

Vector myVector = new Vector();
myVector.add(someCrap); //I can call add as many times as I want,
//It'll handle the gruntwork. I can also remove things from the
//middle and there won't be gaps.


In other words, a vector is a kit that takes care of a bunch of tedious crap that has to be done, and that you'd be doing yourself manually if there were no such thing as vectors.

If you don't understand any of that, you've jumped into the deep end before learning to tread water.

Learn the basics; get a book on programming C# for beginners. One of the boring-looking O'Reilly books with an random-ass animal on the cover that talks about Winforms. Those are fantastic.

Then get into game kits.

Share this post


Link to post
Share on other sites
"I have practically no clue what a Vector is, even though I looked it up on this site"

Vector2 gameBoardDisplayOrigin = new Vector2(70, 89);
i assume its this line that you are talking about?

Vector2 is simply an object that holds 2 numbers. they are usually used as coordinates on a graph (the screen) so this is storing the x and y coordinates for something called gameBoardDisplayOrigin. So when we try to draw the board its going to ask need to know where to draw it ... we are going to draw it at x coordinate 70 and y coordinate 89.
This is a simplified explanation there is more to it.

If you are struggling with c# i can help i am starting some small c# xna projects myself and wouldnt mind helping you at all. Im no guru but we should be able to make some small stuff to help you understand some of the concepts.

Send me a private message if you want to i have AIM (rarely use) Yahoo IM facebook just let me know.

Share this post


Link to post
Share on other sites
A short bit of advise which might be easier said than done:

Don't try to memorize what they're telling you to write. Instead, try to learn why you're writing the code that they're telling you to.

You might know how to declare a variable or create a vector but if you don't know why you want to use one then you're not really learning anything.

Share this post


Link to post
Share on other sites
The key to learning a language is not to learn the "api" or "framework" that it can us. Learn just the basic language.

For C# this is the list of keyword. Now there might be a new ones but this is a pretty good basic list.


abstract
as
base
bool
break
Byte
case
catch
char
checked
class
const
continue
decimal
default
delegate
do
double
else
enum
event
explicit
extern
false
finally
fixed
float
for
foreach
goto
if
implicit
in
int
interface
internal
is
lock
long
namespace
new
null
object
operator
out
override
params
private
protected
public
readonly
ref
return
sbyte
sealed
short
sizeof
stackalloc
static
string
struct
switch
this
throw
true
try
typeof
uint
ulong
unchecked
unsafe
ushort
using
virtual
volatile
void
while


So the first thing you need to do is understand those words, and how to use them to create classes and control the flow of the application.

After you learn that, then all the crazy things you see, Vector2 and the likes are just classes that you will be able to look at and understand how to use.

Learn to crawl before you try flying.

theTroll

Share this post


Link to post
Share on other sites
A lot of good advice in this topic. I've always been stuck trying to figure out what certain things do in the code, but after reading some of the stuff in this topic, it's looking like I may have been looking at the wrong parts.

Either way, this is beneficial to me, thanks.



Also, TheTroll is possibly the best Troll ever.

Share this post


Link to post
Share on other sites
As I am reading the chapter over, to fully understand everything thats going on, I come across the 2 const variables initialized (MaxPlayablePieceIndex), and (EmptyPieceIndex), the text reads:

along with two variables that specify the array index of the last piece that can be placed on the board (MaxPlayablePieceIndex) and of the fake "Empty" piece.

Can someone please explain to me what the heck it's talking about, and what exactly these are used for?

Share this post


Link to post
Share on other sites
I can't without the book, but frequently a programmer decides on certain values. Like for example I may decide that a map is up to 50 units wide. And instead of writing "50" all over my code, I'll write "final int maxWidth = 50;" and everywhere refer to 50.

The upshot is that these variables, like anything else in computing, only mean what we agree that they mean.

Look around and see what's done with them. They are what they do.

Share this post


Link to post
Share on other sites
Thats just it, I semi-know what MaxPlayablePieceIndex does, as I messed with the number, but EmptyPieceIndex on the other hand, does absolutely nothing, so I have no idea why it's initialized, I delete it and the game plays normally.

Share this post


Link to post
Share on other sites
If it does nothing, it is nothing ;)

It reminds me of a figure I have in this program here. I typed this up:

final private static int MARK_NOTDONE = 0;
final private static int MARK_CORRECT = 1;
final private static int MARK_WRONG = 2;


As it turns out, MARK_NOTDONE was never called in the code; at no point do I change a field from CORRECT or WRONG to NOTDONE. They only default that way, and it so happens 0 is how integers initialize in Java so the assignment is never done explictly, and it just so happens I only check if(...CORRECT) else if(...WRONG) and never check against NOTDONE.

Sometimes that happens and then you have a superfluous line.

I commented it out but left it there.

Share this post


Link to post
Share on other sites
I'm starting to think coding would be a lot easier for me, if I wrote down everything that needed to be done. Every small detail, etc.

I don't know if thats good practice.

I have never been an expert at math, I am average at best.

I have a bad habit of not staying focused >_<.
So if I read something, I tend to forget it a sentence later in most cases.

Share this post


Link to post
Share on other sites
Then, you have declared two integer constants that specify the height and width of an individual playing piece in pixels, along with two variables that specify the array index of the last piece that can be placed on the board (MaxPlayablePieceIndex) and of the fake "Empty" piece.

That is exactly what the book says, I just don't see why they'd have us declare a const variable if it does nothing. EmptyPieceIndex sounds like it does something, I just don't know what.

Share this post


Link to post
Share on other sites
Reread my last post. It is something that was meant to do something, or just expressing the writer's thought process, but turned out to do nothing. I thought I would use a MARK_NOTDONE variable and it turned out, after all was said and done, that I did not. Maybe it was used for something but that code was rewritten. Either way, the code can be tossed, but wasn't because they missed it in editing. It is what it does, which apparently is 'nothing'.

One doesn't just dump everything else in final form. You write, then you rewrite things, and sometimes a const or variable here and turn becomes orphaned and sometimes someone forgets to backspace it out.

Share this post


Link to post
Share on other sites
I think your trying too hard to understand another persons code. I consider my self a good programmer and I may have trouble understanding what the writer of that book was trying to do specifically.

I would try doing your own programs, but use the lessons and techniques in the book to give ideas and techniques to program games properly.

It really isn't important that you understand how his game piece works for example, because when you write your own code your game piece will be designed the way you feel is best. If he wanted other people to use his game piece object he should have written it with simple functions to use it.

Share this post


Link to post
Share on other sites
I'm unsure of how well this advice will work for you, but I believe that all the books/tutorials do is show you a working application of the various bits and pieces involved in programming. And if you can see it work, you should be able to know how to apply it to other things.

I used the 3D Buzz videos, as well as the 2D Game tutorials on the XNA site, and when I saw how something worked, I immediately had ideas of how to use it in another game/project.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this