Melompat dan Jatuh

Untuk membuat karakter melompat, kita perlu mengubah koordinat y-nya. Karena titik {0, 0} ada di kiri atas, maka untuk mengubah ketinggian kita harus mengurangi nilai koordinat y. Setelah kita mengubah koordinat, maka kita perlu menjatuhkan karakternya ke bawah hingga kembali ke posisi semula.

Untuk menandai kapan dimulainya lompatan, kita bisa menggunakan event keyboard atau mouse. Supaya lompatan tidak terjadi berkali-kali, kita bisa menggunakan variabel yang menandakan bahwa lompatan sedang dilakukan. Jika karakter yang kita buat melompat sudah kembali ke posisinya, maka kita perlu mengembalikan nilai variabel sebagai tanda bahwa lompatan sudah berakhir.
#include <SDL2/SDL.h>
#include <SDL2/SDL_image.h>
#define jpotongan 3
#define playar 640
#define tlayar 480

SDL_Renderer *trender=NULL;

SDL_Texture *muat_gambar(SDL_Rect *dgambar, const char *s){
SDL_Texture *teksture=NULL;
    SDL_Surface *tmp=IMG_Load(s);
    if(tmp){
        dgambar->w=tmp->w;
        dgambar->h=tmp->h;

        SDL_SetColorKey(tmp, SDL_TRUE, SDL_MapRGB(tmp->format, 0x00, 0xFF, 0xFF));
        teksture=SDL_CreateTextureFromSurface(trender, tmp);
        if(teksture)printf("gagal membuat teksture %s", s);
        else SDL_FreeSurface(tmp);
    }else printf("gagal memuat");
    return teksture;
}

int main(int argc, char* args[]){
    SDL_Window* window = NULL;
    SDL_Event evt;
    int xlatar=0;
    int batas=0;
    int pos=0;
    int lompat=0;
    int ypos=0;
    int x=0;

    if( SDL_Init( SDL_INIT_VIDEO ) < 0 && IMG_Init(IMG_INIT_JPG|IMG_INIT_PNG)){
        printf( "Error: %s\n", SDL_GetError() );
    }else{
        window = SDL_CreateWindow( "SDLku", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, playar, tlayar, SDL_WINDOW_SHOWN );
        if( window == NULL ){
            printf( "Error : %s", SDL_GetError() );
        }else{
            trender = SDL_CreateRenderer(window, -1, SDL_RENDERER_ACCELERATED);
            SDL_Texture *bmp=NULL;
            SDL_Texture *latar=NULL;
            SDL_Rect dgambar;
            unsigned int berikutnya, pkarakter, tkarakter, platar, tlatar;

            bmp=muat_gambar(&dgambar, "animasi.png");
            pkarakter=dgambar.w/jpotongan;
            tkarakter=dgambar.h;

            latar=muat_gambar(&dgambar, "background.png");
            platar=dgambar.w;
            tlatar=dgambar.h;
            batas=platar;
        
            berikutnya=SDL_GetTicks()+70;
            if(bmp!=NULL && latar!=NULL){
                SDL_Rect rct;
            
                while(evt.type!=SDL_QUIT){
                    while(SDL_PollEvent(&evt)){
                        if(evt.type==SDL_MOUSEBUTTONUP || evt.type==SDL_KEYUP){
                            if(lompat==0){
                                ypos=100;
                                lompat=1;
                            }
                        }
                    }

                    SDL_SetRenderDrawColor(trender, 0xFF, 0xFF, 0xFF, 0xFF);
                    SDL_RenderClear(trender);

                    rct.x=xlatar;
                    rct.y=0;
                    rct.w=platar;
                    rct.h=tlayar;
                    SDL_RenderSetViewport(trender, &rct);
            
                    x=0;
                    while(rct.x < 2*playar){
                        SDL_RenderSetViewport(trender, &rct);
                        SDL_RenderCopy(trender, latar, NULL, NULL);
                        rct.x=x-xlatar;
                        x+=platar;
                    }
            
                    rct.x=0;
                    rct.y=tlayar-tkarakter-ypos;
                    rct.w=pkarakter;
                    rct.h=tkarakter;

                    SDL_RenderSetViewport(trender, &rct);

                    rct.x=pkarakter*pos;
                    rct.y=0;
      
                    SDL_RenderCopy(trender, bmp, &rct, NULL);
            
                    SDL_RenderPresent(trender);
            
                    if(SDL_GetTicks()>=berikutnya){
                        berikutnya=SDL_GetTicks()+70;
                        xlatar+=4;
                        if(xlatar>=batas){
                            xlatar=0;
                        }
   
                        if(ypos>0 && lompat!=0){
                            ypos-=4;
                        }else{
                            ypos=0;
                            lompat=0;
                        }
            
                        pos++;
                        if(pos>=jpotongan){
                            pos=0;
                        }
                    }
                }
            }
        }
    }

    SDL_DestroyWindow( window );
    SDL_Quit();

    return 0;
}
Untuk bisa menggunakan program yang dihasilkan kode di atas, kalian perlu dua gambar dengan nama "animasi.png" dan "background.png". Supaya karakter melompat, setelah program dijalankan, kalian perlu menekan tombol keyboard atau mousenya.

Kalau kalian perhatikan, lompatannya terlihat tidak alami. Untuk membuat terlihat lebih natural, kita harus membuat gerakan jatuhnya semakin cepat saat karakter mendekati tanah.
#include <SDL2/SDL.h>
#include <SDL2/SDL_image.h>
#define jpotongan 3
#define playar 640
#define tlayar 480

SDL_Renderer *trender=NULL;

SDL_Texture *muat_gambar(SDL_Rect *dgambar, const char *s){
SDL_Texture *teksture=NULL;
    SDL_Surface *tmp=IMG_Load(s);
    if(tmp){
        dgambar->w=tmp->w;
        dgambar->h=tmp->h;

        SDL_SetColorKey(tmp, SDL_TRUE, SDL_MapRGB(tmp->format, 0x00, 0xFF, 0xFF));
        teksture=SDL_CreateTextureFromSurface(trender, tmp);
        if(teksture)printf("gagal membuat teksture %s", s);
        else SDL_FreeSurface(tmp);
    }else printf("gagal memuat");
    return teksture;
}

int main(int argc, char* args[]){
    SDL_Window* window = NULL;
    SDL_Event evt;
    int xlatar=0;
    int batas=0;
    int pos=0;
    int lompat=0;
    int ypos=0;
    int gravitasi=0;
    int x=0;

    if( SDL_Init( SDL_INIT_VIDEO ) < 0 && IMG_Init(IMG_INIT_JPG|IMG_INIT_PNG)){
        printf( "Error: %s\n", SDL_GetError() );
    }else{
        window = SDL_CreateWindow( "SDLku", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, playar, tlayar, SDL_WINDOW_SHOWN );
        if( window == NULL ){
            printf( "Error : %s", SDL_GetError() );
        }else{
            trender = SDL_CreateRenderer(window, -1, SDL_RENDERER_ACCELERATED);
            SDL_Texture *bmp=NULL;
            SDL_Texture *latar=NULL;
            SDL_Rect dgambar;
            unsigned int berikutnya, pkarakter, tkarakter, platar, tlatar;

            bmp=muat_gambar(&dgambar, "animasi.png");
            pkarakter=dgambar.w/jpotongan;
            tkarakter=dgambar.h;

            latar=muat_gambar(&dgambar, "background.png");
            platar=dgambar.w;
            tlatar=dgambar.h;
            batas=platar;
        
            berikutnya=SDL_GetTicks()+70;
            if(bmp!=NULL && latar!=NULL){
                SDL_Rect rct;
            
                while(evt.type!=SDL_QUIT){
                    while(SDL_PollEvent(&evt)){
                        if(evt.type==SDL_MOUSEBUTTONUP || evt.type==SDL_KEYUP){
                            if(lompat==0){
                                ypos=100;
                                lompat=1;
                                gravitasi=0;
                            }
                        }
                    }

                    SDL_SetRenderDrawColor(trender, 0xFF, 0xFF, 0xFF, 0xFF);
                    SDL_RenderClear(trender);

                    rct.x=xlatar;
                    rct.y=0;
                    rct.w=platar;
                    rct.h=tlayar;
                    SDL_RenderSetViewport(trender, &rct);
            
                    x=0;
                    while(rct.x < 2*playar){
                        SDL_RenderSetViewport(trender, &rct);
                        SDL_RenderCopy(trender, latar, NULL, NULL);
                        rct.x=x-xlatar;
                        x+=platar;
                    }
            
                    rct.x=0;
                    rct.y=tlayar-tkarakter-ypos;
                    rct.w=pkarakter;
                    rct.h=tkarakter;

                    SDL_RenderSetViewport(trender, &rct);

                    rct.x=pkarakter*pos;
                    rct.y=0;
            
                    SDL_RenderCopy(trender, bmp, &rct, NULL);
                    SDL_RenderPresent(trender);
            
                    if(SDL_GetTicks()>=berikutnya){
                        berikutnya=SDL_GetTicks()+70;
                        xlatar+=4;
                        if(xlatar>=batas){
                            xlatar=0;
                        }
            
                        if(ypos>0 && lompat!=0){
                            ypos-=gravitasi;
                            gravitasi+=2;
                        }else{
                            ypos=0;
                            lompat=0;
                            gravitasi=0;
                        }
            
                        pos++;
                        if(pos>=jpotongan){
                            pos=0;
                        }
                    }
                }
            }
        }
    }

    SDL_DestroyWindow( window );
    SDL_Quit();

    return 0;
}

Perbedaan dari kode program di atas dengan kode program sebelumnya adalah adanya variabel gravitasi. Jika kode program sebelumnya selalu menurunkan koordinat y dari karakter 4 pixel. Kode program di atas menurunkan karakter berdasarkan nilai variabel gravitasi yang terus bertambah sesuai jarak dengan posisi awal (atau bisa kita sebut permukaan tanah).