Browse Source

Rendering starts to work again. There is no Z-sorting yet.

legacy
Sam Hocevar sam 14 years ago
parent
commit
a9b63620d4
15 changed files with 181 additions and 137 deletions
  1. +2
    -1
      src/Makefile
  2. +51
    -0
      src/game.cpp
  3. +25
    -0
      src/game.h
  4. +9
    -12
      src/layer.cpp
  5. +4
    -4
      src/layer.h
  6. +5
    -3
      src/map.cpp
  7. +2
    -4
      src/map.h
  8. +45
    -1
      src/scene.cpp
  9. +3
    -1
      src/scene.h
  10. +7
    -13
      src/test-map.cpp
  11. +7
    -0
      src/tiler.cpp
  12. +4
    -0
      src/tiler.h
  13. +13
    -94
      src/tileset.cpp
  14. +3
    -3
      src/tileset.h
  15. +1
    -1
      src/video.cpp

+ 2
- 1
src/Makefile View File

@@ -1,5 +1,6 @@


SRC = test-map.cpp video.cpp tiler.cpp tileset.cpp scene.cpp layer.cpp map.cpp
SRC = test-map.cpp \
game.cpp video.cpp tiler.cpp tileset.cpp scene.cpp layer.cpp map.cpp


all: test-map all: test-map




+ 51
- 0
src/game.cpp View File

@@ -0,0 +1,51 @@

#include "game.h"
#include "map.h"

/*
* Game implementation class
*/

class GameData
{
friend class Game;

private:
Map *map;
int x, y;
int mousex, mousey;
};

/*
* Public Game class
*/

Game::Game(char const *mapname)
{
data = new GameData();
data->map = new Map(mapname);
data->x = data->y = 0;
}

Game::~Game()
{
delete data->map;
delete data;
}

void Game::SetMouse(int x, int y)
{
data->mousex = x;
data->mousey = y;
}

void Game::Render()
{
Scene *scene = new Scene();

data->map->Render(scene, data->mousex, data->mousey, 0);

scene->Render();
delete scene;
}


+ 25
- 0
src/game.h View File

@@ -0,0 +1,25 @@

/*
* The game object
*/

#if !defined __DH_GAME_H__
#define __DH_GAME_H__

class GameData;

class Game
{
public:
Game(char const *mapname);
~Game();

void SetMouse(int x, int y);
void Render();

private:
GameData *data;
};

#endif // __DH_GAME_H__


+ 9
- 12
src/layer.cpp View File

@@ -3,11 +3,11 @@


#include "layer.h" #include "layer.h"


Layer::Layer(int w, int h, int in_z, uint32_t *in_data)
Layer::Layer(int w, int h, int z, uint32_t *in_data)
{ {
width = w; width = w;
height = h; height = h;
z = in_z;
altitude = z;
data = in_data; data = in_data;


#if 0 #if 0
@@ -26,20 +26,17 @@ Layer::~Layer()
free(data); free(data);
} }


void Layer::Draw()
void Layer::Render(Scene *scene, int x, int y, int z)
{ {
for (int y = 0; y < 32; y++)
for (int x = 0; x < 32; x++)
;//tileset->AddTile(GetTile(x, y), x * 32, y * 32, z);
for (int j = 0; j < height; j++)
for (int i = 0; i < width; i++)
if (data[j * width + i])
scene->AddTile(data[j * width + i],
i * 32 - x, j * 32 - y, altitude + z);
} }


int Layer::GetZ() int Layer::GetZ()
{ {
return z;
}

unsigned int Layer::GetTile(int x, int y)
{
return data[y * width + x];
return altitude;
} }



+ 4
- 4
src/layer.h View File

@@ -6,9 +6,10 @@
#if !defined __DH_LAYER_H__ #if !defined __DH_LAYER_H__
#define __DH_LAYER_H__ #define __DH_LAYER_H__


#include <cstdio>
#include <stdint.h> #include <stdint.h>


#include "scene.h"

class Layer class Layer
{ {
public: public:
@@ -16,12 +17,11 @@ public:
~Layer(); ~Layer();


int GetZ(); int GetZ();
unsigned int GetTile(int x, int y);


void Draw();
void Render(Scene *scene, int x, int y, int z);


private: private:
int width, height, z;
int width, height, altitude;
uint32_t *data; uint32_t *data;
}; };




+ 5
- 3
src/map.cpp View File

@@ -56,7 +56,7 @@ Map::Map(char const *path)
/* Read a line, then decide what to do with it. */ /* Read a line, then decide what to do with it. */
fgets(tmp, BUFSIZ, fp); fgets(tmp, BUFSIZ, fp);


if (tiles)
if (tiles && !strchr(tmp, '<'))
{ {
/* We are in the process of reading layer data. Only stop /* We are in the process of reading layer data. Only stop
* when we have read the expected number of tiles. */ * when we have read the expected number of tiles. */
@@ -94,6 +94,7 @@ Map::Map(char const *path)
data->layers[data->nlayers] = new Layer(width, height, level, tiles); data->layers[data->nlayers] = new Layer(width, height, level, tiles);
data->nlayers++; data->nlayers++;
tiles = NULL; tiles = NULL;
//fprintf(stderr, "new layer %ix%i\n", width, height);
} }
} }
else if (sscanf(tmp, " <tileset firstgid=\"%i\"", &i) == 1) else if (sscanf(tmp, " <tileset firstgid=\"%i\"", &i) == 1)
@@ -106,6 +107,7 @@ Map::Map(char const *path)
/* This is a tileset image file. Associate it with firstgid. */ /* This is a tileset image file. Associate it with firstgid. */
data->tilers[data->ntilers] = Tiler::Register(str); data->tilers[data->ntilers] = Tiler::Register(str);
data->ntilers++; data->ntilers++;
//fprintf(stderr, "new tiler %s\n", str);
} }
else if (sscanf(tmp, " <layer name=\"%c%i%c%*[^\"]\" " else if (sscanf(tmp, " <layer name=\"%c%i%c%*[^\"]\" "
"width=\"%i\" height=\"%i\"", &a, &i, &b, &j, &k) == 5) "width=\"%i\" height=\"%i\"", &a, &i, &b, &j, &k) == 5)
@@ -134,9 +136,9 @@ Map::~Map()
delete data; delete data;
} }


void Map::Draw()
void Map::Render(Scene *scene, int x, int y, int z)
{ {
for (int i = 0; i < data->nlayers; i++) for (int i = 0; i < data->nlayers; i++)
data->layers[i]->Draw();
data->layers[i]->Render(scene, x, y, z);
} }



+ 2
- 4
src/map.h View File

@@ -6,9 +6,7 @@
#if !defined __DH_MAP_H__ #if !defined __DH_MAP_H__
#define __DH_MAP_H__ #define __DH_MAP_H__


#include <cstdio>

#include "layer.h"
#include "scene.h"


class MapData; class MapData;


@@ -18,7 +16,7 @@ public:
Map(char const *path); Map(char const *path);
~Map(); ~Map();


void Draw();
void Render(Scene *scene, int x, int y, int z);


private: private:
MapData *data; MapData *data;


+ 45
- 1
src/scene.cpp View File

@@ -1,5 +1,14 @@


#include <stdlib.h>

#include "scene.h" #include "scene.h"
#include "tiler.h"

struct Tile
{
uint32_t prio, code;
int x, y;
};


/* /*
* Scene implementation class * Scene implementation class
@@ -10,7 +19,16 @@ class SceneData
friend class Scene; friend class Scene;


private: private:
int dummy;
static int Compare(void const *p1, void const *p2)
{
Tile const *t1 = (Tile const *)p1;
Tile const *t2 = (Tile const *)p2;

return t1->prio - t2->prio;
}

Tile *tiles;
int ntiles;
}; };


/* /*
@@ -20,6 +38,8 @@ private:
Scene::Scene() Scene::Scene()
{ {
data = new SceneData(); data = new SceneData();
data->tiles = 0;
data->ntiles = 0;
} }


Scene::~Scene() Scene::~Scene()
@@ -27,3 +47,27 @@ Scene::~Scene()
delete data; delete data;
} }


void Scene::AddTile(uint32_t code, int x, int y, int z)
{
if ((data->ntiles % 1024) == 0)
data->tiles = (Tile *)realloc(data->tiles,
(data->ntiles + 1024) * sizeof(Tile));
data->tiles[data->ntiles].prio = 0;
data->tiles[data->ntiles].code = code;
data->tiles[data->ntiles].x = x;
data->tiles[data->ntiles].y = y;
data->ntiles++;
}

void Scene::Render() // XXX: rename to Blit()
{
qsort(data->tiles, data->ntiles, sizeof(Tile), SceneData::Compare);

for (int i = 0; i < data->ntiles; i++)
Tiler::Render(data->tiles[i].code, data->tiles[i].x, data->tiles[i].y);

free(data->tiles);
data->tiles = 0;
data->ntiles = 0;
}


+ 3
- 1
src/scene.h View File

@@ -6,7 +6,6 @@
#if !defined __DH_SCENE_H__ #if !defined __DH_SCENE_H__
#define __DH_SCENE_H__ #define __DH_SCENE_H__


#include <cstdio>
#include <stdint.h> #include <stdint.h>


class SceneData; class SceneData;
@@ -17,6 +16,9 @@ public:
Scene(); Scene();
~Scene(); ~Scene();


void AddTile(uint32_t code, int x, int y, int z);
void Render();

private: private:
SceneData *data; SceneData *data;
}; };


+ 7
- 13
src/test-map.cpp View File

@@ -6,29 +6,23 @@
#include <math.h> #include <math.h>


#include "video.h" #include "video.h"
#include "tiler.h"
#include "map.h"
#include "game.h"


int main(int argc, char **argv) int main(int argc, char **argv)
{ {
Video *video = new Video("Deus Hax", 640, 480); Video *video = new Video("Deus Hax", 640, 480);
Map *map = new Map("maps/testmap-grass.tmx");
Game *game = new Game("maps/testmap-library.tmx");


for (int done = 0; !done; ) for (int done = 0; !done; )
{ {
video->Clear(); video->Clear();


//map->Draw(tiler);

/* Test stuff */ /* Test stuff */
int playerx, playery;
SDL_GetMouseState(&playerx, &playery);
playerx = playerx * (640 - 32) / 640;
playery = playery * (480 - 32) / 480;

//tiler->AddTile(50, playerx, playery, 1);
int mx, my;
SDL_GetMouseState(&mx, &my);
game->SetMouse(mx * (640 - 32) / 640, my * (480 - 32) / 480);


//tiler->Render();
game->Render();
video->Refresh(33.33333f); video->Refresh(33.33333f);


/* This could go in a separate function */ /* This could go in a separate function */
@@ -47,7 +41,7 @@ int main(int argc, char **argv)
} }
} }


delete map;
delete game;
delete video; delete video;


return EXIT_SUCCESS; return EXIT_SUCCESS;


+ 7
- 0
src/tiler.cpp View File

@@ -83,3 +83,10 @@ void Tiler::Deregister(int id)
} }
} }


void Tiler::Render(uint32_t code, int x, int y)
{
int id = (code >> 16) - 1; /* ID 0 is for the empty tileset */

data->tilesets[id]->BlitTile(code & 0xffff, x, y);
}


+ 4
- 0
src/tiler.h View File

@@ -6,11 +6,15 @@
#if !defined __DH_TILER_H__ #if !defined __DH_TILER_H__
#define __DH_TILER_H__ #define __DH_TILER_H__


#include <stdint.h>

class Tiler class Tiler
{ {
public: public:
static int Register(char const *path); static int Register(char const *path);
static void Deregister(int id); static void Deregister(int id);

static void Render(uint32_t code, int x, int y);
}; };


#endif // __DH_TILER_H__ #endif // __DH_TILER_H__


+ 13
- 94
src/tileset.cpp View File

@@ -41,7 +41,6 @@ private:
int ntiles; int ntiles;


GLuint texture[1]; GLuint texture[1];
GLuint buflist[3];
}; };


/* /*
@@ -77,15 +76,11 @@ TileSet::TileSet(char const *path)


glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);

/* Three GPU buffers */
glGenBuffers(3, data->buflist);
} }


TileSet::~TileSet() TileSet::~TileSet()
{ {
glDeleteTextures(1, data->texture); glDeleteTextures(1, data->texture);
glDeleteBuffers(3, data->buflist);


free(data->tiles); free(data->tiles);
free(data->name); free(data->name);
@@ -107,97 +102,21 @@ char const *TileSet::GetName()
return data->name; return data->name;
} }


void TileSet::AddTile(int n, int x, int y, int z)
void TileSet::BlitTile(uint32_t id, int x, int y)
{ {
if ((data->ntiles % 1024) == 0)
{
data->tiles = (int *)realloc(data->tiles,
(data->ntiles + 1024) * 4 * sizeof(int));
}

data->tiles[4 * data->ntiles] = n;
data->tiles[4 * data->ntiles + 1] = x;
data->tiles[4 * data->ntiles + 2] = y;
data->tiles[4 * data->ntiles + 3] = z;

data->ntiles++;
}

void TileSet::Render()
{
/* Sort tiles */
qsort(data->tiles, data->ntiles, 4 * sizeof(int), TileSetData::Compare);

/* Texture coord buffer */
float uvs[8 * data->ntiles];
for (int n = 0; n < data->ntiles; n++)
{
int tile = data->tiles[4 * n];
float ty = .0625f * (tile / 16);
float tx = .0625f * (tile % 16);
uvs[8 * n + 0] = tx;
uvs[8 * n + 1] = ty;
uvs[8 * n + 2] = tx + .0625f;
uvs[8 * n + 3] = ty;
uvs[8 * n + 4] = tx + .0625f;
uvs[8 * n + 5] = ty + .0625f;
uvs[8 * n + 6] = tx;
uvs[8 * n + 7] = ty + .0625f;
}
glBindBuffer(GL_ARRAY_BUFFER, data->buflist[1]);
glBufferData(GL_ARRAY_BUFFER,
8 * data->ntiles * sizeof(float), uvs, GL_STATIC_DRAW);

/* Vertex buffer */
float vertices[8 * data->ntiles];
for (int n = 0; n < data->ntiles; n++)
{
int x = data->tiles[4 * n + 1];
int y = data->tiles[4 * n + 2];
vertices[8 * n + 0] = x;
vertices[8 * n + 1] = y;
vertices[8 * n + 2] = x + 32;
vertices[8 * n + 3] = y;
vertices[8 * n + 4] = x + 32;
vertices[8 * n + 5] = y + 32;
vertices[8 * n + 6] = x;
vertices[8 * n + 7] = y + 32;
}
glBindBuffer(GL_ARRAY_BUFFER, data->buflist[0]);
glBufferData(GL_ARRAY_BUFFER, 8 * data->ntiles * sizeof(float),
vertices, GL_STATIC_DRAW);

/* Index buffer */
int indices[4 * data->ntiles];
for (int n = 0; n < 4 * data->ntiles; n++)
indices[n] = n;
glBindBuffer(GL_ARRAY_BUFFER, data->buflist[2]);
glBufferData(GL_ARRAY_BUFFER, 4 * data->ntiles * sizeof(int),
indices, GL_STATIC_DRAW);

/* Draw everything */
glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glEnableClientState(GL_INDEX_ARRAY);
float tx = .0625f * (id & 0xf);
float ty = .0625f * ((id >> 4) & 0xf);


glBindTexture(GL_TEXTURE_2D, data->texture[0]); glBindTexture(GL_TEXTURE_2D, data->texture[0]);

glBindBuffer(GL_ARRAY_BUFFER, data->buflist[0]);
glVertexPointer(2, GL_FLOAT, 0, NULL);
glBindBuffer(GL_ARRAY_BUFFER, data->buflist[1]);
glTexCoordPointer(2, GL_FLOAT, 0, NULL);
glBindBuffer(GL_ARRAY_BUFFER, data->buflist[2]);
glIndexPointer(GL_INT, 0, NULL);

glDrawArrays(GL_QUADS, 0, 4 * data->ntiles);

glDisableClientState(GL_VERTEX_ARRAY);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
glDisableClientState(GL_INDEX_ARRAY);

/* Empty our shit */
free(data->tiles);
data->tiles = NULL;
data->ntiles = 0;
glBegin(GL_QUADS);
glTexCoord2f(tx, ty);
glVertex2f(x, y);
glTexCoord2f(tx + .0625f, ty);
glVertex2f(x + 32, y);
glTexCoord2f(tx + .0625f, ty + .0625f);
glVertex2f(x + 32, y + 32);
glTexCoord2f(tx, ty + .0625f);
glVertex2f(x, y + 32);
glEnd();
} }



+ 3
- 3
src/tileset.h View File

@@ -6,6 +6,8 @@
#if !defined __DH_TILESET_H__ #if !defined __DH_TILESET_H__
#define __DH_TILESET_H__ #define __DH_TILESET_H__


#include <stdint.h>

class TileSetData; class TileSetData;


class TileSet class TileSet
@@ -19,9 +21,7 @@ public:


char const *GetName(); char const *GetName();


void AddTile(int n, int x, int y, int z);

void Render();
void BlitTile(uint32_t id, int x, int y);


private: private:
TileSetData *data; TileSetData *data;


+ 1
- 1
src/video.cpp View File

@@ -54,7 +54,7 @@ Video::Video(char const *title, int width, int height)


SDL_WM_SetCaption(title, NULL); SDL_WM_SetCaption(title, NULL);
SDL_ShowCursor(0); SDL_ShowCursor(0);
//SDL_WM_GrabInput(SDL_GRAB_ON);
SDL_WM_GrabInput(SDL_GRAB_ON);


/* Initialise OpenGL */ /* Initialise OpenGL */
glViewport(0, 0, data->video->w, data->video->h); glViewport(0, 0, data->video->w, data->video->h);


Loading…
Cancel
Save