Page 5 of 7

Posted: Thu Oct 28, 2004 7:43 pm
by JS Lemming
No really, if you ever divide by 0, blitz says "Error Divide By 0" then crashes. You must have changed some of the mechanics.

Posted: Fri Oct 29, 2004 1:56 pm
by Falco Girgis
I'm at school, so again, I'm not sure exactly what it was. It was something like:

Code: Select all

blood->life = rand() % (intensity/12)
That was actually in the original engine sorta. You're modding by a 0, and modding is just taking the remainder of something after dividing, so yes, it freaks out.

Blitz was something more like this:

Code: Select all

blood/life = Rand(0,intensity/12)
I'm going to assume that your Rand() takes 2 arguments because it does the minimum/maximum thing. I guess that your rand() isn't modding or anything for you. That's really wierd, I wonder how the blitz Rand() works...

Particle Engine is done btw, I'm just making it have more features that'll definately prove to be awesome in the game. It's so smooth and sleek. God, I love this thing.

Posted: Fri Oct 29, 2004 7:00 pm
by MarauderIIC
It internally checks to see if argument 2 is 0 and if it is, it just returns 0?

Posted: Sat Oct 30, 2004 9:45 am
by Falco Girgis
I was finishing up the blood engine when I ran into a decision. One of the things that I'd wanted was to spurt any color of the rainbow. This is the current blood color formula:

Code: Select all

rect_color = SDL_MapRGB(DisplaySurface->format, 255-(max_bloodlife - blood->life)*8, 0, 0);
See, we have the formula that gives us different shades of red depending on the life. Obviously, red, blue, and green (and different combinations) are the only colors that could use that math. I was thinking that the function prototype could be like this:

Code: Select all

void CreateBlood(int x, int y, int angle, int intensity, unsigned short int color, unsigned short int r, unsigned short int g, unsigned short int b);
You pass an x, and y coordinate, the angle of the blood, the intensity.

Then, you have color. 1 is red, 2 is green, 3 is blue and 4- whatever can be hybrid things like this:

Code: Select all

rect_color = SDL_MapRGB(DisplaySurface->format, 255-(max_bloodlife - blood->life)*8, 0, 255-(max_bloodlife - blood->life)*8);
Just mixing the red and the blue. Assuming, that you do this, whatever you pass to r, g, b is going to be ignored.

But, if you enter a 0 in color, whatever you pass to r, g, b will be the actual color of the blood. It won't have the fancy shades, but it will be able to do any color.

What do you guys think? That's the best solution I could come up with. Try to let me know soon so that I can finish this monstrosity.

Posted: Sat Oct 30, 2004 11:25 am
by Falco Girgis
JSL, can you post some enemy code (AI and stuff) from Mario TLC?

I was thinking that when I'm done with the blood, I could start making enemies. I'm trying to get it to where we can make levels ASAP.

Posted: Sat Oct 30, 2004 1:28 pm
by JS Lemming
LEVELS LEVELS LEVELS!!!!!!!!!!! I can't stand it! I am currently working on the main engine functions like image splicing and map rendering! I will work on the level editor LATER!!!! Swuuuuh. Ok, let me see. Here is just some super simple gumba code from the mario game.

Code: Select all

;Updates goombas that are in existance
Function g_UpdateGoomba(DeleteAll)

	;Loop through all goombas
	For cur.Goomba = Each Goomba

	;lower goomba's invincible
	If cur\invincible > 0 Then cur\invincible = cur\invincible - 1

		;Check if he is on hard mode
		If cur\hard = True

			If Distance(Mario\x+16,Mario\y+32,cur\x+16,cur\y) < 220


				If cur\x < Mario\x-40 Then cur\xvel = 3
				If cur\x > Mario\x+40 Then cur\xvel = -3

				If cur\jump = False And solid((cur\x/32),(cur\y/32)+1) = 1
				
					cur\jump = True
					cur\jumptimer = Rand(7,9)
					
				EndIf
			EndIf
			
		EndIf


		;Keep Goomba in map array range
		If cur\x < 32 Then cur\x = 32 : cur\xvel = 2
		If cur\y < 32 Then cur\y = 32 : cur\yvel = 2
		If (cur\x + 32) > (MapWD*32)+32 Then cur\x = (MapWD*32) - 64+32 : cur\xvel = 0
		If (cur\y + 32) > (MapHT*32)+32 Then cur\y = (MapHT*32) - 32+32 : cur\yvel = 0

		;Check if goomba has hit a wall
		If solid(((cur\x-1)/32),(cur\y/32)) = 1 Then cur\xvel = 2
		If solid(((cur\x+1+32)/32),(cur\y/32)) = 1 Then cur\xvel = -2

		
		;Check if goomba about to fall off legde
		If solid(((cur\x-1)/32),((cur\y+40)/32)) = 0 And cur\jump = False Then cur\xvel = 2
		If solid(((cur\x+1+32)/32),((cur\y+40)/32)) = 0 And cur\jump = False Then cur\xvel = -2	



		;Check if goomba hits another goomba
		For temp.Goomba = Each Goomba
		
			If cur\x > temp\x And cur\x < temp\x + 32
				If cur\y > temp\y-2 And cur\y < temp\y + 34
			
				If cur\x < temp\x+15 Then cur\xvel = -2 : temp\xvel = 2
				If cur\x > temp\x+15 Then cur\xvel = 2 : temp\xvel = -2

				EndIf
			EndIf

		Next
		
		;Cycle through all bullets to see if they are hit
		For bul.Bullet = Each Bullet
		
			If bul\x > cur\x And bul\x < cur\x+32
				If bul\y > cur\y And bul\y < cur\y+32
				
					cur\xvel = cur\xvel*2
				
					cur\life = cur\life - 1
					
					PlaySound S_BulletHit
					
					;blood spray
					g_CreateBlood(bul\x,bul\y,(-bul\xvel)/2,200)
					
					DrawImage P_Bang,bul\x-BaseX,bul\y-BaseY
					Delete bul	

				
				EndIf
			EndIf
		
		Next


		;If goomba jumping
		If cur\jump = True And cur\jumptimer > 0
		
	
			cur\yvel = cur\yvel - 0.8
			cur\jumptimer = cur\jumptimer - 1
	
		Else

			;Simulate Gravity
			cur\yvel = cur\yvel + Gravity
	
		EndIf


		;Left Right Movement
		For i = 1 To Abs(cur\xvel)

			BoundLeft	= (cur\x + 0)
			BoundRight	= (cur\x + 32)
			BoundTop	= (cur\y + 0)
			BoundBottom	= (cur\y + 32)

			For b = BoundTop To BoundBottom-1;
	
			MoveLeft = False
			MoveRight = False
	
			If cur\xvel < 0
	
				If Solid((BoundLeft-1)/32,b/32) = 1

					cur\xvel = 0
					Exit
					
				Else
					
					MoveLeft = True
				
				EndIf
				
			EndIf
			
			If cur\xvel > 0
				
				If Solid((BoundRight+1)/32,b/32) = 1

					cur\xvel = 0
					Exit
					
				Else

					MoveRight = True
	
				EndIf
				
			EndIf
		
			Next
			
			If MoveLeft = True Then cur\x = cur\x - 1
			If MoveRight = True Then cur\x = cur\x + 1
			
		Next




		;Up and Down movement
		For i = 1 To Abs(cur\yvel)
		
			BoundLeft	= (cur\x + 0)
			BoundRight	= (cur\x + 32)
			BoundTop	= (cur\y + 0)
			BoundBottom	= (cur\y + 31)

			For b = BoundLeft To BoundRight
	
			MoveUp = False
			MoveDown = False
	
			If cur\yvel < 0
	
				If Solid(b/32,(BoundTop-1)/32) = 1

					cur\yvel = 0
					Exit
					
				Else
					
					MoveUp = True
				
				EndIf
				
			EndIf
			
			If cur\yvel > 0
				
				If Solid(b/32,(BoundBottom+1)/32) = 1
				
					cur\yvel = 0
					cur\jump = False
					Exit
					
				Else

					MoveDown = True
	
				EndIf
				
			EndIf
		
			Next
			
			If MoveUp = True Then cur\y = cur\y - 1
			If MoveDown = True Then cur\y = cur\y + 1
			
		Next

		



		;Check if Mario has touched the goomba
		If Mario\x+32 > cur\x+4 And Mario\x+32 < cur\x+60
		
			;if mario stomps goomba, bounce him
			If Mario\y+64 > cur\y+0 And Mario\y+64 < cur\y+9
		
				Mario\y = cur\y-64
				Mario\yvel = -Mario\yvel*1.3
			
				g_CreateBlood(cur\x,cur\y+10,-2,Abs(Mario\yvel*18))
				g_CreateBlood(cur\x,cur\y+10,2,Abs(Mario\yvel*18))
			
				PlaySound S_Crush
			
				If cur\invincible = 0
			
					cur\xvel = cur\xvel * 2
			
					cur\life = cur\life - 1
					
					cur\invincible = 10
					
				EndIf
				
			EndIf
			
			;if mario tuoches goomba's side, hurt mario
			If Mario\y+64 > cur\y+25 And Mario\y+64 < cur\y+65;34
		
				If Mario\x < cur\x+15
					Mario\xvel = -cur\xvel
					If cur\xvel < 0 Then Mario\xvel = cur\xvel*2 : cur\xvel = -cur\xvel
				EndIf
				
				If Mario\x > cur\x+15
					Mario\xvel = -cur\xvel
					If cur\xvel > 0 Then Mario\xvel = cur\xvel*2 : cur\xvel = -cur\xvel
				EndIf
				
				g_CreateBlood(Mario\x+16,Mario\y+32,cur\xvel*2,280)
		
				;Mario only takes damage if he is not invincible
				If Mario\invincible = 0
			
					PlaySound S_Doh
			
					Mario\life = Mario\life - 1
				
					Mario\invincible = 10
					
				EndIf
				
			EndIf
		EndIf
		
		;kill it if its out of life
		If cur\life < 1 Then DeleteThis = True : EnemiesKilled = EnemiesKilled + 1
		
		;Animate goomba
		If cur\framecounter < 1
		
			cur\frame = cur\frame + 1
			If cur\frame > 1 Then cur\frame = 0
			cur\framecounter = 5
			
		Else
			cur\framecounter = cur\framecounter - 1
		EndIf	
		

		;Draw goomba
		DrawImage P_Goomba,cur\x-BaseX,cur\y-BaseY,cur\frame

		;Delete this coin if need
		If DeleteAll = True Then DeleteThis = True
		
		;If coin needs to be deleted do so
		If DeleteThis = True Then Delete cur : DeleteThis = False

	Next

End Function

Posted: Sat Oct 30, 2004 2:54 pm
by MarauderIIC
JS: We should probably split up your code into multiple functions. For example,
JS Lemming wrote:

Code: Select all

;Updates goombas that are in existance
		;Check if Mario has touched the goomba
		If Mario\x+32 > cur\x+4 And Mario\x+32 < cur\x+60
		
			;if mario stomps goomba, bounce him
			If Mario\y+64 > cur\y+0 And Mario\y+64 < cur\y+9
		
				Mario\y = cur\y-64
				Mario\yvel = -Mario\yvel*1.3
Could be something like:

Code: Select all

void marioMove(/* ... */) {
/* ... */
    char hitDir;
    for(vector<Enemies*>::iterator it;it = enemies.begin();it != enemies.end()) {
        //Check entity collision
        hitDir = entCollide(player, *it);
        if(hitDir && hitDir != 'U') {
            doDamage(player, it->dmgAmount());
            break; //?
        }
    }
/* ... */
}

char entCollide(Actor* who, Actor* hitWhat) {
    int wx = who->xCoord();
    int wy = who->yCoord();
    int wr = who->rightOffset();
    int wl = who->leftOffset();
    int wu = who->upOffset();
    int wd = who->downOffset();
    int hx = hitWhat->xCoord();
    int hy = hitWhat->yCoord();
    int hr = hitWhat->rightOffset();
    int hl = hitWhat->leftOffset();
    int hu = hitWhat->upOffset();
    int hd = hitWhat->downOffset();

    if ((wx + wr) > (hx + hl) && (wx + wl) < (hx + hl))
    { //if x-coords increase as they go right....
        return 'L';
    }
    else if ((wx + wr) > (hx + hr) && (wx + wl) < (hx + hr))
    {
        return 'R';
    }
    else if ((wy + wd) > (hy + hu) && (wy + wu) > (hy + hu))
    { //if y-coords increase as they go up....
        //some sort of "hitWhat can be hurt by upward attack" flag.
        //return uppercase for one and lowercase for another.
        return 'U';
    }
    /*.... etc ....*/
    //if all fail:
    return 0; //the null character -- character 0. aka '\0'
}

Code: Select all

void CreateBlood(int x, int y, int angle, int intensity, unsigned short int color, unsigned short int r, unsigned short int g, unsigned short int b);
Might rather be

Code: Select all

void CreateBlood(int x, int y, int angle, int intensity, unsigned short int color, unsigned short int r = 0, unsigned short int g = 0, unsigned short int b = 0);
So you can just specify color. Or:

Code: Select all

void CreateBlood(int x, int y, int angle, int intensity, unsigned short int r, unsigned short int g, unsigned short int b, unsigned short int color = 0);
If you think you'll use rgb specification the most often.

Posted: Sat Oct 30, 2004 3:10 pm
by JS Lemming
Heh, trust me. Almost all the code from my old mario game is really crusty. It was my first shot at a kinda big project, and I wasn't to smooth in the programmin.

Posted: Sat Oct 30, 2004 9:12 pm
by Falco Girgis
Shouldn't the goomba functions be inside of the goomba class so that they have access to member variables?
MarauderIIC wrote:

Code: Select all

void CreateBlood(int x, int y, int angle, int intensity, unsigned short int color, unsigned short int r, unsigned short int g, unsigned short int b);
Might rather be

Code: Select all

void CreateBlood(int x, int y, int angle, int intensity, unsigned short int color, unsigned short int r = 0, unsigned short int g = 0, unsigned short int b = 0);
:!!!!:
JS Lemming wrote:Heh, trust me. Almost all the code from my old mario game is really crusty.
:lol:

Posted: Sat Oct 30, 2004 10:16 pm
by MarauderIIC
GyroVorbis wrote:Shouldn't the goomba functions be inside of the goomba class so that they have access to member variables?
I made entCollide() a general function. Now you only need one entity collision function: that one.

Posted: Sat Oct 30, 2004 10:49 pm
by Falco Girgis
MarauderIIC wrote:
GyroVorbis wrote:Shouldn't the goomba functions be inside of the goomba class so that they have access to member variables?
I made entCollide() a general function. Now you only need one entity collision function: that one.
Yeah, good idea.

NEStix: Programming (C++/SDL)

Posted: Sun Oct 31, 2004 6:46 am
by JS Lemming
I thought it would be best to start organizing some stuff, so I broke away from the original topic.

Ok, here is my first SDL program. It graphicly demonstrates my Rectangle collision function. Give'er a compile or two.

Code: Select all

//demo of object collision detection by JS Lemming

//requires static linkage to:  
//sdl.lib, sdlmain.lib

//requires dynamic linkage to: 
//sdl.dll

//include SDL stuff
#include "sdl.h"

//include ability to exit program
#include <stdlib.h>


//screen dimensions
const int SCREEN_WIDTH=640;
const int SCREEN_HEIGHT=480;

//display surface
SDL_Surface* g_pDisplaySurface;

//event structure
SDL_Event g_Event;

//rectangle
SDL_Rect g_Rect;

//color components
Uint8 g_Red, g_Green, g_Blue;

//color value
Uint32 g_Color;


//Box class
class Box
{
    public:
        int x, y;
        int xvel, yvel;
        int width, height;
        int red, green, blue;
};

//Returns true if the two rectangles are overlapping
bool RectsOverlap(int x1,int y1,int width1,int height1,int x2,int y2,int width2,int height2) {
    if((x1+width1 > x2) && (x1 < x2+width2)) {
        if((y1+height1 > y2) && (y1 < y2+height2)) {
            return true;
        }
    }
    return false;
}



//main function
int main(int argc, char* argv[])
{
	//initialize SDL
	if (SDL_Init(SDL_INIT_VIDEO)==-1)
	{
		//error initializing SDL

		//report the error
		fprintf(stderr,"Could not initialize SDL!\n");

		//end the program
		exit(1);
	}
	else
	{
		//SDL initialized

		//report success
		fprintf(stdout,"SDL initialized properly!\n");

		//set up to uninitialize SDL at exit
		atexit(SDL_Quit);
	}

    //hide mouse
    SDL_ShowCursor(SDL_DISABLE);

	//create windowed environment
	g_pDisplaySurface = SDL_SetVideoMode(SCREEN_WIDTH,SCREEN_HEIGHT,24,SDL_ANYFORMAT|SDL_FULLSCREEN);

	//error check
	if (g_pDisplaySurface == NULL)
	{
		//report error
		fprintf(stderr,"Could not set up display surface!\n");

		//exit the program
		exit(1);
	}

    //Create 2 instances of class box
    Box box1;
    box1.x = 40;
    box1.y = 30;
    box1.xvel = 0;
    box1.yvel = 0;
    box1.width = 50;
    box1.height = 50;
    box1.red = 0;
    box1.green = 200;
    box1.blue = 0;

    Box box2;
    box2.x = 300;
    box2.y = 200;
    box2.xvel = 0;
    box2.yvel = 0;
    box2.width = 80;
    box2.height = 80;
    box2.red = 0;
    box2.green = 0;
    box2.blue = 255;

	//main game loop
    while(1)
	{
        //look for an event
        if(SDL_PollEvent( &g_Event ) == true)
        {
            //if user closes out of window, exit loop
            if(g_Event.type==SDL_QUIT)
                break;

            //if ESC key
            if(g_Event.key.keysym.sym == SDLK_ESCAPE )
            {
                // if ESC was pressed, quit the program.
                SDL_Event quit;
                quit.type = SDL_QUIT;
                SDL_PushEvent( &quit );
            }

            //check key input
            switch( g_Event.type )
            {
                //if a key is pressed
                case SDL_KEYDOWN:
                    switch( g_Event.key.keysym.sym )
                    {
                        case SDLK_UP:
                            box1.yvel = -1;
                            break;
                        case SDLK_DOWN:
                            box1.yvel = 1;
                            break;
                        case SDLK_LEFT:
                            box1.xvel = -1;
                            break;
                        case SDLK_RIGHT:
                            box1.xvel = 1;
                            break;
                    }
                    break;

                //a key is released
                case SDL_KEYUP:
                    switch( g_Event.key.keysym.sym )
                    {
                        case SDLK_UP:
                            if(box1.yvel < 0)
                                box1.yvel = 0;
                            break;
                        case SDLK_DOWN:
                            if(box1.yvel > 0)
                                box1.yvel = 0;
                            break;
                        case SDLK_LEFT:
                            if(box1.xvel < 0)
                                box1.xvel = 0;
                            break;
                        case SDLK_RIGHT:
                            if(box1.xvel > 0)
                                box1.xvel = 0;
                            break;
                    }
                    break;

                default:
                    break;
            }
        }

        //Check to see if they are overlapping
        if(RectsOverlap(box1.x,box1.y,box1.width,box1.height,
        box2.x,box2.y,box2.width,box2.height) == true)
        {
            //clear the screen with white
            SDL_FillRect(g_pDisplaySurface, NULL, SDL_MapRGB( g_pDisplaySurface->format, 255, 255, 255 ));
        }
        else
        {
            //clear the screen with black
            SDL_FillRect(g_pDisplaySurface, NULL, SDL_MapRGB( g_pDisplaySurface->format, 0, 0, 0 ));
        }

        //update the first box
        //adjust coords based on velocity
        box1.x = box1.x + box1.xvel;
        box1.y = box1.y + box1.yvel;

        //create the rectangle
        g_Rect.x = box1.x;
        g_Rect.y = box1.y;
        g_Rect.w = box1.width;
        g_Rect.h = box1.height;

        //set the color
        g_Red=box1.red;
        g_Green=box1.green;
        g_Blue=box1.blue;
        g_Color=SDL_MapRGB(g_pDisplaySurface->format,g_Red,g_Green,g_Blue);

        //fill the rectangle
        SDL_FillRect(g_pDisplaySurface,&g_Rect,g_Color);


        //update the second box
        //create the rectangle
        g_Rect.x = box2.x;
        g_Rect.y = box2.y;
        g_Rect.w = box2.width;
        g_Rect.h = box2.height;

        //set the color
        g_Red    = box2.red;
        g_Green  = box2.green;
        g_Blue   = box2.blue;
        g_Color  = SDL_MapRGB(g_pDisplaySurface->format,g_Red,g_Green,g_Blue);

        //fill the rectangle
        SDL_FillRect(g_pDisplaySurface,&g_Rect,g_Color);



        //update the screen
        SDL_UpdateRect(g_pDisplaySurface,0,0,0,0);
	}

	//normal termination
	fprintf(stdout,"Terminating normally.\n");

	//return to OS
	return(0);
}

Posted: Thu Nov 18, 2004 4:19 pm
by Falco Girgis
Guys, I'm seriously looking into compiling a small perl interpretter into a C/++ program. If this works how I hope, it could be SUPER useful. Harnessing the power of Perl at our disposal. Subroutines that can take any amount of arguments, no different data types, etc. Perl is a VERY powerful language.

Don't get the wrong idea though. It's C++ here. But every now and again... it'd be so nice to be able to bust out the perl for things that are super hard in C++ and trivial in perl.

I want to see how much worse an SDL app is efficiency wise with perl. How would I go about doing that?

Also, its not like the engine will be perl or anything, so whatever small things perl does do probably won't really make a difference. I would like to know though...

Posted: Fri Nov 19, 2004 7:23 am
by JS Lemming
How could perl be better then c++ in anything besides working with string and text things, which the game would not have much of or any.

Posted: Fri Nov 19, 2004 10:18 am
by Guest
How can you start programming without one? Oh, and I may have one..