Welcome, Guest. Please login or register.

Login with username, password and session length

 
Advanced search

1411498 Posts in 69373 Topics- by 58428 Members - Latest Member: shelton786

April 25, 2024, 08:35:44 AM

Need hosting? Check out Digital Ocean
(more details in this thread)
TIGSource ForumsDeveloperTechnical (Moderator: ThemsAllTook)ProgramGamer toys around in C++
Pages: [1] 2
Print
Author Topic: ProgramGamer toys around in C++  (Read 3099 times)
ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« on: August 07, 2015, 04:13:37 AM »

So, I've been messing with C++ again lately, and I thought I'd post about my adventures in Stroustrup land.  Beer!

So, for the first post, I've been toying with SDL2 and it's functions lately. I downloaded Lazy Foo's tutorial file and started extrapolating that into something. So far there are color cycling, easing functions and inverted color cube movement. Here's the code:

(also epilepsy warning I guess even though the color cycling is not that fast and the screen size is not that big)

Code:
//Using SDL and standard IO
#include <SDL.h>
#include "stdio.h"

//Screen dimension constants
const int SCREEN_WIDTH = 256;
const int SCREEN_HEIGHT = 192;

int EaseInOutQuad(double t,double b,double c,double d)
{
//t: current time
//b: start value
//c: change in value
//d: duration
t /= d/2;
if (t < 1) return c/2*t*t + b;
t--;
return -c/2 * (t*(t-2) - 1) + b;
}


int main( int argc, char* args[] )
{
//The window we'll be rendering to
SDL_Window* window = NULL;

//The surface contained by the window
SDL_Surface* screenSurface = NULL;

//Screen buffer
SDL_Surface* screenBuffer = NULL;

//Initialize SDL
if( SDL_Init( SDL_INIT_VIDEO ) < 0 )
{
printf( "SDL could not initialize! SDL_Error: %s\n", SDL_GetError() );
}
else
{
//Create window
window = SDL_CreateWindow( "SDL Tutorial", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, SCREEN_WIDTH, SCREEN_HEIGHT, SDL_WINDOW_SHOWN );
if( window == NULL )
{
printf( "Window could not be created! SDL_Error: %s\n", SDL_GetError() );
}
else
{
//Get window surface
screenSurface = SDL_GetWindowSurface( window );

//Create a surface
screenBuffer = SDL_CreateRGBSurface(0,SCREEN_WIDTH,SCREEN_HEIGHT,32,0,0,0,0);
if (screenBuffer == NULL)
            {
                printf( "Could not create buffer! SDL_Error: %s\n", SDL_GetError() );
            }

//Game loop
bool running = true;
SDL_Event event;
int colorRed = 255;
int colorGreen = 255;
int colorBlue = 255;
int const increment = 1;
            int x = 0;
            int y = 0;
int xSpeed = 0;
int ySpeed = 0;
while (running)
            {
                //Event handling
                while (SDL_PollEvent(&event))
                {
                    if (event.type == SDL_QUIT)
                    {
                        running = false;
                    }
                    else if (event.type == SDL_KEYDOWN)
                    {
                        if (event.key.keysym.scancode == SDL_SCANCODE_LEFT)
                        {
                            xSpeed = -4;
                        }
                        else if (event.key.keysym.scancode == SDL_SCANCODE_RIGHT)
                        {
                            xSpeed = 4;
                        }
                        else if (event.key.keysym.scancode == SDL_SCANCODE_UP)
                        {
                            ySpeed = -4;
                        }
                        else if (event.key.keysym.scancode == SDL_SCANCODE_DOWN)
                        {
                            ySpeed = 4;
                        }
                    }
                    else if (event.type == SDL_KEYUP)
                    {
                        if (event.key.keysym.scancode == SDL_SCANCODE_LEFT)
                        {
                            xSpeed = 0;
                        }
                        else if (event.key.keysym.scancode == SDL_SCANCODE_RIGHT)
                        {
                            xSpeed = 0;
                        }
                        else if (event.key.keysym.scancode == SDL_SCANCODE_UP)
                        {
                            ySpeed = 0;
                        }
                        else if (event.key.keysym.scancode == SDL_SCANCODE_DOWN)
                        {
                            ySpeed = 0;
                        }
                    }
                }

                //Moves the player around
                x += xSpeed;
                y += ySpeed;

                //Cycle through colors
                if (colorRed < 255 && colorGreen == 0 && colorBlue == 0)
                {
                    colorRed += increment;
                }
                else if (colorRed == 255 && colorGreen < 255 && colorBlue == 0)
                {
                    colorGreen += increment;
                }
                else if (colorRed > 0 && colorGreen == 255 && colorBlue == 0)
                {
                    colorRed -= increment;
                }
                else if (colorRed == 0 && colorGreen == 255 && colorBlue < 255)
                {
                    colorBlue += increment;
                }
                else if (colorRed == 0 && colorGreen > 0 && colorBlue == 255)
                {
                    colorGreen -= increment;
                }
                else if (colorRed < 255 && colorGreen == 0 && colorBlue == 255)
                {
                    colorRed += increment;
                }
                else if (colorRed == 255 && colorGreen == 0 && colorBlue > 0)
                {
                    colorBlue -= increment;
                }
                else if (colorRed > 0 && colorGreen == 255 && colorBlue == 255)
                {
                    colorRed -= increment;
                }

                //Draw a colored rectangle to the screen
                SDL_FillRect(screenBuffer, NULL, SDL_MapRGB(screenSurface->format,EaseInOutQuad(colorRed,0,255,255),EaseInOutQuad(colorGreen,0,255,255),EaseInOutQuad(colorBlue,0,255,255)));

                //Draw a square on top of this
                SDL_Rect rect;
                rect.x = x;
                rect.y = y;
                rect.w = 32;
                rect.h = 32;
                SDL_FillRect(screenBuffer, &rect, SDL_MapRGB(screenSurface->format,255 - EaseInOutQuad(colorRed,0,255,255),255 - EaseInOutQuad(colorGreen,0,255,255),255 - EaseInOutQuad(colorBlue,0,255,255)));

                //Blit the buffer to the screen surface
                if (SDL_BlitSurface(screenBuffer,NULL,screenSurface,NULL)!=0)
                {
                    printf( "Window could not be blit! SDL_Error: %s\n", SDL_GetError() );
                }

                //Update the surface
                SDL_UpdateWindowSurface( window );

                //Wait one frame
                SDL_Delay(17);
            }
//Free the surface after game loop
SDL_FreeSurface(screenBuffer);
}
}
//Destroy window
SDL_DestroyWindow( window );

//Quit SDL subsystems
SDL_Quit();

return 0;
}

So yeah, I had to deal with SDL's input system, which is... great. Having to cycle through a stack of inputs is just fine and not at all tedious. I had less trouble drawing to the screen surprisingly, and was even able to make an intermediate level color cycling routine. I even ported an easing function to make it smoother, which worked wonderfully! The only issue I can find is that clicking and dragging the window pauses the program for some reason, so I'll look into that next.
Logged

JWki
Level 4
****


View Profile
« Reply #1 on: August 07, 2015, 05:07:13 AM »

SDL's message loop is simply a wrapper over the message loop of whatever OS you are using, so it's not really designed to provide a nice input system, it's just not that high level and it shouldn't. Despite the many people using SDL as "engine", it's mainly a platform abstraction layer with some additional rendering capabilities. It's something to build an engine on top of.
Logged
ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« Reply #2 on: August 07, 2015, 05:27:42 AM »

I agree, it's really not an engine by itself, but can be made into an engine with relative ease thanks to its functions and structures. Speaking of which, I should probably make some kind of controller object to alleviate the main function of all that input looping. I would just have to call a "CheckInput" method to empty the input queue and could just call another "GetInput" method to return a bool whether a key has been pressed or not. That would be practical.
Logged

Cheezmeister
Level 3
***



View Profile
« Reply #3 on: August 07, 2015, 07:56:01 PM »

SDL's input API is pretty dope for what it is. So's the rest of it, for that matter. Truly superb design from some real OG gamedevs.

The fact that it's NOT an engine makes it reliable, flexible, portable, and generally a minimal pain in the arse compared to anything else I've tried. Is it tedious to write your own input loop? Well, sure, a little, but it's not rocket science either.

Here we have a solid input translator in under 100 lines, that offers NES controls and then some. It ain't engine-caliber, but it covers all of my bases, and probably most of yours. (From https://github.com/Cheezmeister/jamboot)

Code:
Input handle_input()
{
    Input ret = {0};

    // Process events first
    SDL_Event event;
    while (SDL_PollEvent(&event) )
    {
        if (event.type == SDL_QUIT) ret.quit = true;
        if (event.type == SDL_KEYDOWN && event.key.keysym.sym == SDLK_ESCAPE) ret.quit = true;

        // Window resize
        if (event.type == SDL_WINDOWEVENT)
        {
            if (event.window.event == SDL_WINDOWEVENT_RESIZED)
            {
                int x = event.window.data1;
                int y = event.window.data2;
                viewport.x = x;
                viewport.y = x;
                int max = x > y ? x : y;
                glViewport(0, 0, max, max);
            }
        }

        // Gamepad buttons
        if (event.type == SDL_CONTROLLERBUTTONDOWN)
        {
            if (event.cbutton.button & SDL_CONTROLLER_BUTTON_A)
            {
                ret.action.prime = true;
            }
        }
        // Keyboard presses
        if (event.type == SDL_KEYDOWN)
        {
            if (event.key.keysym.sym == SDLK_SPACE)
            {
                ret.action.prime = true;
            }
        }
    }

    // Poll the current state of the mouse
    struct _Mouse {
        Uint8 buttons;
        int x;
        int y;
    } mouse;
    mouse.buttons = SDL_GetMouseState(&mouse.x, &mouse.y);
    ret.held.prime |= (mouse.buttons & SDL_BUTTON(1));
    ret.axes.x2 = mouse.x * 2.0 / viewport.x - 1.0;
    ret.axes.y2 = mouse.y * 2.0 / viewport.y - 1.0;
    ret.axes.y2 *= -1;


    // Poll the current state of the keyboard
    const Uint8* keystate = SDL_GetKeyboardState(NULL);
    ret.axes.y1  = 1.0 * (keystate[SDL_SCANCODE_UP]);
    ret.axes.y1 -= 1.0 * (keystate[SDL_SCANCODE_DOWN]);
    ret.axes.x1  = 1.0 * (keystate[SDL_SCANCODE_RIGHT]);
    ret.axes.x1 -= 1.0 * (keystate[SDL_SCANCODE_LEFT]);

    // Poll the gamepad sticks
    ret.axes.x3 = SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_LEFTX) / (float)32767;
    ret.axes.x4 = SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_RIGHTX) / (float)32767;
    ret.axes.y3 = SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_LEFTY) / (float)32767;
    ret.axes.y4 = SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_RIGHTY) / (float)32767;

    // Poll gamepad buttons
    ret.held.aux = SDL_GameControllerGetButton(controller, SDL_CONTROLLER_BUTTON_RIGHTSHOULDER);

    return ret;
}


Logged

෴Me෴ @chzmstr | www.luchenlabs.com ቒMadeቓ RA | Nextris | Chromathud   ᙍMakingᙌCheezus II (Devlog)
ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« Reply #4 on: August 08, 2015, 03:44:01 AM »

Oh, wow, the architecture on that is quite amazing! You have a class called Input which you use as your return type and which you fill with input info every time you call the function handle_input(). That is a new level of smarts for me, I salute you good sir(s?)!

Also, thank you for providing that, I was working on something else and I was going completely the wrong way. I was creating an entire class for controllers with virtual keys and stuff like that, your method is way simpler and still as efficient. The only thing I can see that could improve it would be to make handle_input() a member of a class which keeps track of virtual keys so that you could have remappable buttons. Thanks to you sir and have a good day! Beer!
Logged

ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« Reply #5 on: August 08, 2015, 04:46:59 PM »

To add to this, I messed around with SDL's ability to detect touch input with my new surface pro, and it was surprisingly easy to program with SDL's events, so I stand corrected on the matter I guess Shrug
Logged

Cheezmeister
Level 3
***



View Profile
« Reply #6 on: August 08, 2015, 10:10:52 PM »

Thanks for the kinds words. Though, as I said...it's really not rocket science. This is rocket science Smiley

SDL makes everything super easy. You have Sam Lantinga & co. to thank for that, I just make crappy games with it =] I would, however, be very interested in seeing your touch handling code.
Logged

෴Me෴ @chzmstr | www.luchenlabs.com ቒMadeቓ RA | Nextris | Chromathud   ᙍMakingᙌCheezus II (Devlog)
ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« Reply #7 on: August 09, 2015, 04:33:40 PM »

Wow... I was trying to make an enemy object and I just tried to put the definition of the class in a .cpp file and the implementation in a .h. Someone get c++ away from me as quickly as possible...  Facepalm
Logged

ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« Reply #8 on: August 12, 2015, 04:42:09 PM »

Alrighty, I can't figure this one out. I am clearly calling five different SDL_FillRect functions here, why are they not showing up on the screen???
Code:
#include <stdio.h>
#include <math.h>
#include "SDL.h"

using namespace std;

const int windowWidth = 800;
const int windowHeight = 450;

int main(int argc, char *argv[])
{
    //Initiation function
    if (SDL_Init(SDL_INIT_EVERYTHING))
    {
        printf("SDL Not initiated for some reason.");
    }

    //Creating a window
    SDL_Window* window = SDL_CreateWindow("Game",300,50,windowWidth,windowHeight,0);
    if (window == NULL)
    {
        printf("Window not created for some reason");
    }

    //Getting the window's surface
    SDL_Surface* surface = SDL_GetWindowSurface(window);
    if (surface == NULL)
    {
        printf("Surface not retrieved for some reason");
    }

    SDL_Surface* buffer = SDL_CreateRGBSurface(0,windowWidth,windowHeight,32,0,0,0,255);

    //Setting up game loop variables and memory in general
    bool running = true;
    double x = 0;
    double y = 0;
    int square_x = 0;
    int square_y = 0;
    int red = 0;
    int green = 0;
    int blue = 0;
    SDL_Event event;
    //Rectangle areas
    SDL_Rect bar_1;
    bar_1.w = windowWidth / 16;
    bar_1.h = windowHeight;

    SDL_Rect area_1;
    area_1.w = windowWidth / 16 * 4;
    area_1.h = windowHeight;
    area_1.x = bar_1.x + bar_1.w;

    SDL_Rect bar_2_1;
    SDL_Rect bar_2_2;
    bar_2_1.w = windowWidth / 16;
    bar_2_1.h = windowHeight;
    bar_2_1.x = area_1.x + area_1.w;

    SDL_Rect area_2;
    area_2.w = windowWidth / 16 * 9;
    area_2.h = windowHeight;
    area_2.x = bar_2_1.x + bar_2_1.w;

    SDL_Rect bar_3;
    bar_3.w = windowWidth / 16;
    bar_3.h = windowHeight;
    bar_3.x = area_2.x + area_2.w;

    SDL_Rect enemy;
    enemy.w = area_1.w / 3;
    enemy.h = area_1.w / 3;
    SDL_Rect cursor;
    cursor.w = (windowWidth / 8);
    cursor.h = (windowHeight / 8);
    //Enemy variables (they're special)
    int enemies = 30;
    bool enemy_active[enemies];
    int enemy_y[enemies];
    int enemy_green[enemies];
    int enemy_blue[enemies];

    //Game loop
    while (running)
    {
        //Event handling
        while (SDL_PollEvent(&event))
        {
            if (event.type == SDL_QUIT)
            {
                running = false;
            }
            if (event.type == SDL_FINGERDOWN)
            {
                x = event.tfinger.x * windowWidth - 16;
                green = event.tfinger.x * 255;
                y = event.tfinger.y * windowHeight - 16;
                blue = event.tfinger.y * 255;
            }
            if (event.type == SDL_FINGERMOTION)
            {
                x += event.tfinger.dx * windowWidth;
                green = event.tfinger.x * 255;
                y += event.tfinger.dy * windowHeight;
                blue = event.tfinger.y * 255;
            }
        }
        square_x = x;
        square_y = y;
        square_x = square_x - (square_x % (windowWidth / 8));
        square_y = square_y - (square_y % (windowHeight / 8));

        //Enemy routine
        /*
        for (int i = 0;i < enemies;i ++)
        {

        }
        */

        //Color scaling
        if (red < 255)
        {
            red += 5;
        }

        //Rendering!
        SDL_FillRect(buffer,&bar_1, SDL_MapRGB(surface->format,255-red,0,0));
        SDL_FillRect(buffer,&area_1, SDL_MapRGB(surface->format,red,green,blue));
        SDL_FillRect(buffer,&bar_2_1, SDL_MapRGB(surface->format,255-red,0,0));
        SDL_FillRect(buffer,&area_2, SDL_MapRGB(surface->format,red,green,blue));
        SDL_FillRect(buffer,&bar_3, SDL_MapRGB(surface->format,255-red,0,0));
        cursor.x = square_x;
        cursor.y = square_y;
        SDL_BlitSurface(buffer,NULL,surface,NULL);
        SDL_UpdateWindowSurface(window);

        //Adding delay for framerate reasons
        SDL_Delay(16);
    }
    //Cleaning up buffer
    SDL_FreeSurface(buffer);

    //Cleaning up the window
    SDL_DestroyWindow(window);

    //Cleaning up SDL
    SDL_Quit();

    //Returning 0
    return 0;
}
Logged

ThemsAllTook
Administrator
Level 10
******



View Profile WWW
« Reply #9 on: August 12, 2015, 07:15:02 PM »

Looks like bar_1.x and bar_1.y are uninitialized, so you're probably getting garbage values outside the bounds of your window. All the others seem to be based on the same uninitialized values, so if the first one is offscreen, they all will be.
Logged

ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« Reply #10 on: August 13, 2015, 02:06:07 AM »

Oh... I thought those got initialised to zero in the object's constructor... Well, thanks for the help! I'll go fix this incredibly trivial bug with horrible consequences.
Logged

Cheezmeister
Level 3
***



View Profile
« Reply #11 on: August 13, 2015, 06:52:19 PM »

Oh... I thought those got initialised to zero in the object's constructor... Well, thanks for the help!

What is this "object" you speak of? What is a "constructor"?

Somewhere, far away, Sam and Bjarne are reading this and stifling giggles.
Logged

෴Me෴ @chzmstr | www.luchenlabs.com ቒMadeቓ RA | Nextris | Chromathud   ᙍMakingᙌCheezus II (Devlog)
Cheezmeister
Level 3
***



View Profile
« Reply #12 on: August 13, 2015, 06:54:22 PM »

By which I mean, SDL is a virgin C library. SDL_Rect is a struct, not a class. It doesn't have a constructor and if it did I doubt it'd initialize anything by default.
Logged

෴Me෴ @chzmstr | www.luchenlabs.com ቒMadeቓ RA | Nextris | Chromathud   ᙍMakingᙌCheezus II (Devlog)
ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« Reply #13 on: August 13, 2015, 07:40:17 PM »

Right, I keep forgetting that too, that must be why it's so well made and easy to use. I would have thought some things to be classes though, like surfaces or things like that, but I guess passing a pointer to a function is fine too for simulating member functions.
Logged

ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« Reply #14 on: August 18, 2015, 06:50:32 PM »

Code:
#include <iostream>
#include <math.h>
#include "SDL.h"

using namespace std;

const int WindowX = 400;
const int WindowY = 250;
const int WindowWidth = 600;
const int WindowHeight = 400;

double timeRate = 1;

int tile_x(int tileID)
{
    return (tileID % 4) * 16;
}

int tile_y(int tileID)
{
    return floor(tileID / 4) * 16;
}

int sign(int argument)
{
    if (argument > 0)
    {
        return 1;
    }
    else if (argument < 0)
    {
        return -1;
    }
    else
    {
        return 0;
    }
}

struct MY_Input
{
    bool quit = false;
    bool up = false;
    bool down = false;
    bool left = false;
    bool right = false;
    bool space = false;

    void update(SDL_Event* event)
    {
        while (SDL_PollEvent(event))
        {
            if (event->type == SDL_QUIT)
            {
                quit = true;
            }
            else if (event->type == SDL_KEYDOWN)
            {
                if (event->key.keysym.sym == SDLK_SPACE)
                {
                    space = true;
                }
                if (event->key.keysym.sym == SDLK_w)
                {
                    up = true;
                }
                if (event->key.keysym.sym == SDLK_s)
                {
                    down = true;
                }
                if (event->key.keysym.sym == SDLK_a)
                {
                    left = true;
                }
                if (event->key.keysym.sym == SDLK_d)
                {
                    right = true;
                }
            }
            else if (event->type == SDL_KEYUP)
            {
                if (event->key.keysym.sym == SDLK_SPACE)
                {
                    space = false;
                }
                if (event->key.keysym.sym == SDLK_w)
                {
                    up = false;
                }
                if (event->key.keysym.sym == SDLK_s)
                {
                    down = false;
                }
                if (event->key.keysym.sym == SDLK_a)
                {
                    left = false;
                }
                if (event->key.keysym.sym == SDLK_d)
                {
                    right = false;
                }
            }
        }
    }
};

struct MY_Player
{
    double x = 0;//Pixels
    double y = 0;//Pixels
    double xSpeed = 0;//Pixels per frame
    double ySpeed = 0;//Pixels per frame
    double xSpeedPrev = 0;//Pixels per frame
    double ySpeedPrev = 0;//Pixels per frame
    double xMaxSpeed = 4;//Pixels per frame
    double yMaxSpeed = 6;//Pixels per frame
    double jumpSpeed = 6;//Pixels per frame
    double gravity = 0.25;//Pixels per frame squared
    double acceleration = 0.5;//Pixels per frame squared

    //Creating player surface
    SDL_Surface* playerSurface;

    MY_Player()
    {
        //Initializing player surface
        playerSurface = SDL_LoadBMP("resource_images/player.bmp");
    }
    ~MY_Player()
    {
        //Freeing player surface
        SDL_FreeSurface(playerSurface);
    }

    void update(MY_Input* input)
    {
        if (input->left && !input->right)
        {
            xSpeed -= (acceleration * timeRate);
            if (xSpeed < -xMaxSpeed)
            {
                xSpeed = -xMaxSpeed;
            }
        }
        else if (input->right && !input->left)
        {
            xSpeed += (acceleration * timeRate);
            if (xSpeed > xMaxSpeed)
            {
                xSpeed = xMaxSpeed;
            }
        }
        else
        {
            xSpeed -= sign(xSpeed) * (acceleration * timeRate);
            if (abs(xSpeed) < (acceleration * timeRate))
            {
                xSpeed = 0;
            }
        }
        x += (acceleration * timeRate) * ((xSpeedPrev + xSpeed) / 2);


        if (input->up && y == 200)
        {
            ySpeed = -8;
        }

        ySpeed += (gravity * timeRate);
        if (ySpeed > yMaxSpeed)
        {
            ySpeed = yMaxSpeed;
        }

        y += (acceleration * timeRate) * ((ySpeedPrev + ySpeed) / 2);

        if (y > 200)
        {
            y = 200;
            ySpeed = 0;
        }

        xSpeedPrev = xSpeed;
        ySpeedPrev = ySpeed;
    }
};

struct MY_Renderer
{
    SDL_Rect rect1;
    SDL_Rect rect2;
    MY_Renderer()
    {
        rect1.x = tile_x(0);
        rect1.y = tile_y(0);
        rect1.w = 16;
        rect1.h = 16;
        rect2.x = 0;
        rect2.y = 0;
        rect2.w = 16;
        rect2.h = 16;
    }
    void draw(SDL_Surface* buffer,MY_Player* player)
    {
        //Clear the buffer
        SDL_FillRect(buffer,NULL,SDL_MapRGB(buffer->format,0,0,0));

        //Blit the player tile sprite to the buffer
        rect2.x = player->x;
        rect2.y = player->y;
        SDL_BlitSurface(player->playerSurface,&rect1,buffer,&rect2);
    }
};

int main(int argc, char *argv[])
{
    //Init SDL
    SDL_Init(SDL_INIT_EVERYTHING);

    //Create window
    SDL_Window* window = SDL_CreateWindow("Game",WindowX,WindowY,WindowWidth,WindowHeight,SDL_WINDOW_ALLOW_HIGHDPI);

    //Getting the window's surface
    SDL_Surface* windowSurface = SDL_GetWindowSurface(window);

    //Creating buffer
    SDL_Surface* buffer = SDL_CreateRGBSurface(0,WindowWidth,WindowHeight,32,0,0,0,0);

    //Creating tile surface
    SDL_Surface* tile = SDL_LoadBMP("resource_images/tileset_1.bmp");

    //Initiating game loop
    bool running = true;
    SDL_Event event;
    MY_Input input;
    MY_Player player;
    MY_Renderer renderer;
    long int ticks = 0;

    while (running)
    {
        //Update ticks
        ticks = SDL_GetTicks();
        ticks += 16;

        //Get input
        input.update(&event);

        //Update player
        player.update(&input);

        //Render everything to the buffer
        renderer.draw(buffer,&player);

        //Blit the buffer to the screen surface
        SDL_BlitSurface(buffer,NULL,windowSurface,NULL);

        //Updating the screen with the window!
        SDL_UpdateWindowSurface(window);

        //Checking if we quit the program
        if (input.quit)
        {
            running = false;
        }

        //Wait one frame
        if (ticks > SDL_GetTicks())
        {
            SDL_Delay(ticks - SDL_GetTicks());
        }
    }

    //Freeing tile surface
    SDL_FreeSurface(tile);

    //Freeing buffer surface
    SDL_FreeSurface(buffer);

    //Destroy window
    SDL_DestroyWindow(window);

    //Quit SDL
    SDL_Quit();
    return 0;
}

If anyone is willing to parse through this, I'd like some feedback on my code so far, since I don't usually program in C++. I used to have everything in the main function but I broke down everything in structures and functions. I'd like to know if I did a good job or not hehehe.
Logged

oahda
Level 10
*****



View Profile
« Reply #15 on: August 19, 2015, 01:52:08 AM »

Nice to have it confirmed that STL does lack sign(), as I've too implemented it myself instead. I'd actually never heard of the function in all my years programming in C++ until I saw it in a Unity C# tutorial and now I use it all the time in both languages.

Mine is shorter and looks something like this: return (argument < 0) ? -1 : ((argument > 0) ? 1 : 0);

Also you don't need to use {} if there's only one expression (with a semicolon at the end).
Logged

oahda
Level 10
*****



View Profile
« Reply #16 on: August 19, 2015, 01:56:12 AM »

All in all this kind of looks more like a C program than a C++ program with all those structs instead of classes with all public members. Might want to look into that. Also you're still seemingly putting everything into the same file altho you're no longer putting everything in the main function. Might want to split stuff up a bit? Learn how to do classes properly with a header and a source file? You generally put the class definition in a .h or .hpp header file and the implementation in a .cpp source file and then just include the header from where you need the class.
Logged

ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« Reply #17 on: August 19, 2015, 09:34:28 AM »

I tried separating everything into source and header files, and now my compiler returns "build failed" with no errors. What the fuck Stroustrup?

Edit: found the bug. Turns out that trying to make variables global in c++ is guaranteed to backfire.
« Last Edit: August 19, 2015, 10:02:44 AM by ProgramGamer » Logged

ThemsAllTook
Administrator
Level 10
******



View Profile WWW
« Reply #18 on: August 19, 2015, 10:13:11 AM »

Edit: found the bug. Turns out that trying to make variables global in c++ is guaranteed to backfire.

I'm not sure if there's a more C++ way to do it, but the C way is to declare globals as extern in a header, and put the non-extern definition in the corresponding implementation file. That way they're visible to anything that includes the header, and the linker will resolve them to a single location.
Logged

ProgramGamer
Administrator
Level 10
******


aka Mireille


View Profile
« Reply #19 on: August 19, 2015, 10:50:08 AM »

I did that, that's how I fixed the bug. My problem was that I had constants in there too, so I had to declare them extern in their implementation too.

Edit: I was toying around with trigonometry and weird bugs kept creeping up. Turns out I put a += where an = was supposed to be and the c++ trig functions use radians (I was assuming they used degrees). This is the programming equivalent of forgetting to change the mode of your calculator!
« Last Edit: August 19, 2015, 05:30:33 PM by ProgramGamer » Logged

Pages: [1] 2
Print
Jump to:  

Theme orange-lt created by panic