jump_timer_.tick(dt); | jump_timer_.tick(dt); | ||||
// Break block | // Break block | ||||
if (ctx.game.isMousePressed(sf::Mouse::Button::Left)) | |||||
if (ctx.game.isMousePressed(SDL_BUTTON_LEFT)) | |||||
ctx.plane.breakBlock(mouse_tile_); | ctx.plane.breakBlock(mouse_tile_); | ||||
// Move left | // Move left | ||||
if (ctx.game.isKeyPressed(sf::Keyboard::A) || ctx.game.isKeyPressed(sf::Keyboard::Left)) { | |||||
if (ctx.game.isKeyPressed(SDL_SCANCODE_A) || ctx.game.isKeyPressed(SDL_SCANCODE_LEFT)) { | |||||
body_.force_ += Swan::Vec2(-FORCE, 0); | body_.force_ += Swan::Vec2(-FORCE, 0); | ||||
state_ = State::RUNNING_L; | state_ = State::RUNNING_L; | ||||
} | } | ||||
// Move right | // Move right | ||||
if (ctx.game.isKeyPressed(sf::Keyboard::D) || ctx.game.isKeyPressed(sf::Keyboard::Right)) { | |||||
if (ctx.game.isKeyPressed(SDL_SCANCODE_D) || ctx.game.isKeyPressed(SDL_SCANCODE_RIGHT)) { | |||||
body_.force_ += Swan::Vec2(FORCE, 0); | body_.force_ += Swan::Vec2(FORCE, 0); | ||||
if (state_ == State::RUNNING_L) | if (state_ == State::RUNNING_L) | ||||
state_ = State::IDLE; | state_ = State::IDLE; | ||||
} | } | ||||
// Jump | // Jump | ||||
if (body_.on_ground_ && ctx.game.isKeyPressed(sf::Keyboard::Space) && jump_timer_.periodic(0.5)) { | |||||
if (body_.on_ground_ && ctx.game.isKeyPressed(SDL_SCANCODE_SPACE) && jump_timer_.periodic(0.5)) { | |||||
body_.vel_.y = -JUMP_FORCE; | body_.vel_.y = -JUMP_FORCE; | ||||
} | } | ||||
float deactivate_timer_ = DEACTIVATE_INTERVAL; | float deactivate_timer_ = DEACTIVATE_INTERVAL; | ||||
struct Visuals { | struct Visuals { | ||||
std::unique_ptr<SDL_Texture, void (*)(SDL_Texture *)> texture_{nullptr, SDL_DestroyTexture}; | |||||
std::unique_ptr<SDL_Surface, void (*)(SDL_Surface *)> surface_{nullptr, SDL_FreeSurface}; | |||||
bool dirty_; | bool dirty_; | ||||
}; | }; | ||||
std::unique_ptr<Visuals> visuals_; | std::unique_ptr<Visuals> visuals_; |
namespace Swan { | namespace Swan { | ||||
sf::Uint8 *Chunk::renderbuf = new sf::Uint8[CHUNK_WIDTH * TILE_SIZE * CHUNK_HEIGHT * TILE_SIZE * 4]; | |||||
uint8_t *Chunk::renderbuf = new uint8_t[CHUNK_WIDTH * TILE_SIZE * CHUNK_HEIGHT * TILE_SIZE * 4]; | |||||
Tile::ID *Chunk::getTileData() { | Tile::ID *Chunk::getTileData() { | ||||
keepActive(); | keepActive(); | ||||
if (!isCompressed()) | if (!isCompressed()) | ||||
return; | return; | ||||
uint8_t *dest = new uint8_t[CHUNK_WIDTH * CHUNK_HEIGHT * sizeof(Tile::ID)]; | |||||
auto dest = std::make_unique<uint8_t[]>(CHUNK_WIDTH * CHUNK_HEIGHT * sizeof(Tile::ID)); | |||||
uLongf destlen = CHUNK_WIDTH * CHUNK_HEIGHT * sizeof(Tile::ID); | uLongf destlen = CHUNK_WIDTH * CHUNK_HEIGHT * sizeof(Tile::ID); | ||||
int ret = uncompress( | int ret = uncompress( | ||||
dest, &destlen, | |||||
dest.get(), &destlen, | |||||
(Bytef *)data_.get(), compressed_size_); | (Bytef *)data_.get(), compressed_size_); | ||||
if (ret != Z_OK) { | if (ret != Z_OK) { | ||||
fprintf(stderr, "Decompressing chunk failed: %i\n", ret); | fprintf(stderr, "Decompressing chunk failed: %i\n", ret); | ||||
delete[] dest; | |||||
abort(); | abort(); | ||||
} | } | ||||
data_.reset(dest); | |||||
data_ = std::move(dest); | |||||
visuals_.reset(new Visuals()); | visuals_.reset(new Visuals()); | ||||
visuals_->tex_.create(CHUNK_WIDTH * TILE_SIZE, CHUNK_HEIGHT * TILE_SIZE); | |||||
visuals_->sprite_ = sf::Sprite(); | |||||
visuals_->surface_.reset(SDL_CreateRGBSurface( | |||||
0, CHUNK_WIDTH * TILE_SIZE, CHUNK_HEIGHT * TILE_SIZE, 24, 0, 0, 0, 0)); | |||||
visuals_->dirty_ = true; | visuals_->dirty_ = true; | ||||
need_render_ = true; | need_render_ = true; | ||||
fprintf(stderr, "Decompressed chunk %i,%i from %li bytes to %lu bytes.\n", | fprintf(stderr, "Decompressed chunk %i,%i from %li bytes to %lu bytes.\n", | ||||
pos_.x, pos_.y, compressed_size_, CHUNK_WIDTH * CHUNK_HEIGHT * sizeof(Tile::ID)); | pos_.x, pos_.y, compressed_size_, CHUNK_WIDTH * CHUNK_HEIGHT * sizeof(Tile::ID)); | ||||
compressed_size_ = -1; | compressed_size_ = -1; | ||||
tile = &ctx.world.getTileByID(id); | tile = &ctx.world.getTileByID(id); | ||||
} | } | ||||
/* | |||||
const sf::Uint8 *imgptr = NULL; | const sf::Uint8 *imgptr = NULL; | ||||
//const sf::Uint8 *imgptr = tile->image->getPixelsPtr(); | //const sf::Uint8 *imgptr = tile->image->getPixelsPtr(); | ||||
for (int imgy = 0; imgy < TILE_SIZE; ++imgy) { | for (int imgy = 0; imgy < TILE_SIZE; ++imgy) { | ||||
pixx * 4; | pixx * 4; | ||||
memcpy(pix, imgptr + imgy * TILE_SIZE * 4, TILE_SIZE * 4); | memcpy(pix, imgptr + imgy * TILE_SIZE * 4, TILE_SIZE * 4); | ||||
} | } | ||||
*/ | |||||
} | } | ||||
} | } | ||||
visuals_->tex_.update(renderbuf, CHUNK_WIDTH * TILE_SIZE, CHUNK_HEIGHT * TILE_SIZE, 0, 0); | |||||
//visuals_->tex_.update(renderbuf, CHUNK_WIDTH * TILE_SIZE, CHUNK_HEIGHT * TILE_SIZE, 0, 0); | |||||
visuals_->dirty_ = true; | visuals_->dirty_ = true; | ||||
} | } | ||||
} | } | ||||
if (visuals_->dirty_) { | if (visuals_->dirty_) { | ||||
visuals_->sprite_.setTexture(visuals_->tex_); | |||||
//visuals_->sprite_.setTexture(visuals_->tex_); | |||||
visuals_->dirty_ = false; | visuals_->dirty_ = false; | ||||
} | } | ||||
win.setPos(pos_ * Vec2i(CHUNK_WIDTH, CHUNK_HEIGHT)); | win.setPos(pos_ * Vec2i(CHUNK_WIDTH, CHUNK_HEIGHT)); | ||||
win.draw(visuals_->sprite_); | |||||
//win.draw(visuals_->sprite_); | |||||
} | } | ||||
void Chunk::tick(float dt) { | void Chunk::tick(float dt) { |
#include <dlfcn.h> | #include <dlfcn.h> | ||||
#include <math.h> | #include <math.h> | ||||
#include <SFML/Window/Mouse.hpp> | |||||
#include <time.h> | #include <time.h> | ||||
#include <memory> | #include <memory> | ||||
#include "World.h" | #include "World.h" | ||||
#include <SFML/System/Clock.hpp> | |||||
#include "Game.h" | #include "Game.h" | ||||
#include "Win.h" | #include "Win.h" | ||||
namespace Swan { | namespace Swan { | ||||
static bool chunkLine(int l, sf::Clock &clock, WorldPlane &plane, ChunkPos &abspos, const Vec2i &dir) { | |||||
static bool chunkLine(int l, WorldPlane &plane, ChunkPos &abspos, const Vec2i &dir) { | |||||
for (int i = 0; i < l; ++i) { | for (int i = 0; i < l; ++i) { | ||||
plane.getChunk(abspos); | plane.getChunk(abspos); | ||||
// Don't blow our frame budget on generating chunks, | // Don't blow our frame budget on generating chunks, | ||||
// but generate as many as possible within the budget | // but generate as many as possible within the budget | ||||
if (clock.getElapsedTime().asSeconds() > 1.0 / 100) | |||||
return true; | |||||
//if (clock.getElapsedTime().asSeconds() > 1.0 / 100) | |||||
// return true; | |||||
abspos += dir; | abspos += dir; | ||||
} | } | ||||
} | } | ||||
void World::ChunkRenderer::tick(WorldPlane &plane, ChunkPos abspos) { | void World::ChunkRenderer::tick(WorldPlane &plane, ChunkPos abspos) { | ||||
sf::Clock clock; | |||||
int l = 0; | int l = 0; | ||||
for (int i = 0; i < 4; ++i) { | for (int i = 0; i < 4; ++i) { | ||||
if (chunkLine(l, clock, plane, abspos, Vec2i(0, -1))) break; | |||||
if (chunkLine(l, clock, plane, abspos, Vec2i(1, 0))) break; | |||||
if (chunkLine(l, plane, abspos, Vec2i(0, -1))) break; | |||||
if (chunkLine(l, plane, abspos, Vec2i(1, 0))) break; | |||||
l += 1; | l += 1; | ||||
if (chunkLine(l, clock, plane, abspos, Vec2i(0, 1))) break; | |||||
if (chunkLine(l, clock, plane, abspos, Vec2i(-1, 0))) break; | |||||
if (chunkLine(l, plane, abspos, Vec2i(0, 1))) break; | |||||
if (chunkLine(l, plane, abspos, Vec2i(-1, 0))) break; | |||||
l += 1; | l += 1; | ||||
} | } | ||||
} | } |
#include "WorldPlane.h" | #include "WorldPlane.h" | ||||
#include <math.h> | #include <math.h> | ||||
#include <SFML/System/Clock.hpp> | |||||
#include <iostream> | #include <iostream> | ||||
#include "World.h" | #include "World.h" | ||||
ent->draw(getContext(), win); | ent->draw(getContext(), win); | ||||
if (debug_boxes_.size() > 0) { | if (debug_boxes_.size() > 0) { | ||||
sf::RectangleShape rect(Vec2(TILE_SIZE, TILE_SIZE)); | |||||
rect.setFillColor(sf::Color(60, 70, 200, 100)); | |||||
rect.setOutlineThickness(1); | |||||
rect.setOutlineColor(sf::Color(50, 65, 170, 200)); | |||||
for (auto &pos: debug_boxes_) { | |||||
win.setPos(pos); | |||||
win.draw(rect); | |||||
} | |||||
//sf::RectangleShape rect(Vec2(TILE_SIZE, TILE_SIZE)); | |||||
//rect.setFillColor(sf::Color(60, 70, 200, 100)); | |||||
//rect.setOutlineThickness(1); | |||||
//rect.setOutlineColor(sf::Color(50, 65, 170, 200)); | |||||
//for (auto &pos: debug_boxes_) { | |||||
// win.setPos(pos); | |||||
// win.draw(rect); | |||||
//} | |||||
} | } | ||||
} | } | ||||