2D Изометрический (ромбовидный) игровой движок — Обратные спрайты

Все мои спрайты меняются местами, когда я пытаюсь нарисовать свою изометрическую карту.

Вот файл tileset.png, упомянутый в следующем коде:
введите описание изображения здесь

Object.h / Object.cpp

Я могу использовать их для рисования плиток, элементов пользовательского интерфейса и т. Д.

#pragma once

class Object {
public:
//FUNCTIONS
Object();
void addComponent(float value);
int getComponent(float index);
void editComponent(float index, float value);
void deleteComponent(float index);

private:
vector<int> components;
};

#include "Object.cpp"

#pragma once

//FUNCTIONS
Object::Object() {
//...
}

void Object::addComponent(float value) {
components.push_back(value);
}

int Object::getComponent(float index) {
return components[index];
}

void Object::editComponent(float index, float value) {
components[index] = value;
}

void Object::deleteComponent(float index) {
components.erase(components.begin() + index);
}

Замечания: У меня может быть странное включение, я борюсь с визуальной студией, ха-ха.

Scene.h / Scene.cpp

Обрабатывать данные & графика

#pragma once

class Scene {
public:
Scene(float w, float h, int mapx, int mapy, int tilesize, int mapwidth, int mapheight);
void run();

void addLayer();
void loadTileset(sf::String url);
void loadUiTileset(sf::String url);

//functions
//...

//getters
//...

//setters
//...

private:
sf::RenderWindow window;

float width;
float height;

int nb_layers;

int map_x;
int map_y;
int map_width;
int map_height;
int tile_size;
int selected_tile_index;

sf::RenderTexture texture;
sf::Sprite tile;
sf::Sprite map;
sf::Texture tileset;
vector<Object> tiles;

sf::Texture uiTileset;

//private functions
void updateMap();

//...

void processEvent();
void update(sf::Time deltaTime);
void render();

//...
};

#include "Scene.cpp"

#pragma once

//functions
Scene::Scene(float w, float h, int mapx, int mapy, int tilesize, int mapwidth, int mapheight) : window(sf::VideoMode(w, h), "Editor") {
width = w;
height = h;

map_x = mapx;
map_y = mapy;
map_width = mapwidth;
map_height = mapheight;

tile_size = tilesize;

selected_tile_index = 0;//default

nb_layers = 0;
}

void Scene::run() {
sf::Clock clock;
sf::Time timeSinceLastUpdate = sf::Time::Zero;
sf::Time TimePerFrame = sf::seconds(1.f / 60.f);

while (window.isOpen()) {
processEvent();

timeSinceLastUpdate += clock.restart();

while (timeSinceLastUpdate > TimePerFrame) {
timeSinceLastUpdate -= TimePerFrame;

processEvent();
update(TimePerFrame);
}

render();
}
}

void Scene::addLayer() {
nb_layers += 1;

int tile_x = map_x,
tile_y = map_y,
num_layer = nb_layers - 1,
layer_pos = (num_layer * tile_size) / 2,
tile_zOrder = -1;

tile_y -= layer_pos;

int x = map_x,
y = map_y;

for (int h = 0; h < map_height; h++) {
for (int w = 0; w < map_width; w++) {
tile_zOrder = (w * (h + 1)) + (num_layer * 10);

x = carthesianToIsometric(tile_x, tile_y)[0];
y = carthesianToIsometric(tile_x, tile_y)[1] - layer_pos;

cout << x << ", " << y << endl;

Object tile;
tile.addComponent(selected_tile_index);
tile.addComponent(x);
tile.addComponent(y);
tile.addComponent(tile_zOrder);
tile.addComponent(num_layer);

tiles.push_back(tile);
tile_x += tile_size;
}
tile_x = 0;
tile_y += tile_size;
}

updateMap();
}

void Scene::loadTileset(sf::String url) {
if (!tileset.loadFromFile(url))
{
cout << std::string(url) << "couldn't be loaded..." << endl;
}
}

void Scene::loadUiTileset(sf::String url) {
if (!uiTileset.loadFromFile(url))
{
cout << std::string(url) << "couldn't be loaded..." << endl;
}
}

//getters
//...

//setters
//...

//private functions
void Scene::updateMap() {
int tile_position_x = 0,
tile_position_y = 0;

int tile_x = 0,
tile_y = 0;

if (!texture.create(map_width * tile_size, (map_height * tile_size) / 2))
cout << "Texture couldn't be loaded... " << endl;

texture.clear(sf::Color(133, 118, 104, 255));

sf::Sprite image;
image.setTexture(tileset);
int tileset_width = image.getGlobalBounds().width,
tileset_height = image.getGlobalBounds().height;

tile.setTexture(tileset);

for (int tile_index = 0; tile_index < tiles.size(); tile_index++) {
tile_position_x = getTilePosition(tileset_width, tileset_height, tiles[tile_index].getComponent(0), tile_size)[0];
tile_position_y = getTilePosition(tileset_width, tileset_height, tiles[tile_index].getComponent(0), tile_size)[1];

tile.setTextureRect(sf::IntRect(tile_position_x, tile_position_y, tile_size, tile_size));

tile_x = tiles[tile_index].getComponent(1);
tile_y = tiles[tile_index].getComponent(2);

tile.setPosition(sf::Vector2f(tile_x, tile_y));

texture.draw(tile);
}

map.setTexture(texture.getTexture());
}

void Scene::processEvent() {
sf::Event event;

while (window.pollEvent(event)) {
switch (event.type) {
case sf::Event::Closed:
window.close();
break;

case sf::Event::KeyPressed:
if (event.key.code == sf::Keyboard::Escape)
window.close();
break;
}
}
}

void Scene::update(sf::Time deltaTime) {
//REMEMBER: distance = speed * time
//MOVEMENT, ANIMATIONS ETC. ..
}

void Scene::render() {
window.clear();

window.draw(map);

window.display();
}

main.cpp

#pragma once
//global functions + main headers + class headers =>
#include "globalfunctions.h"
int main() {
int map_width = 15,
map_height = 15,
tile_size = 64;

float scene_width = map_width * tile_size,
scene_height = (map_height * tile_size) / 2;

Scene engine(scene_width, scene_height, 0, 0, tile_size, map_width, map_height);
engine.loadTileset("tileset.png");
//engine.loadUiTileset("menu.png");

engine.addLayer();
//...

engine.run();
return EXIT_SUCCESS;
}

globalfunctions.h

Некоторые служебные функции.
getTilePosition (…) позволяет мне получить x, y для текстуры с заданным индексом плитки. Пример: если я хочу нарисовать плитку № 0 текстуры тайла.

#pragma once
#include <SFML/System.hpp>
#include <SFML/Graphics.hpp>
#include <SFML/Window.hpp>
#include <iostream>
#include <math.h>
#include <vector>

using namespace std;

vector<float> getTilePosition(float tileset_width, float tileset_height, float tile_index, float tile_size) {//In a tileset
float tileX = 0,
tileY = 0,
tilePerLine = 0;

tilePerLine = tileset_width / tile_size;

tileY = floor(tile_index / tilePerLine);
tileX = ((tile_index + 1) - (tileY * tilePerLine)) - 1;

tileX *= tile_size;
tileY *= tile_size;

vector<float> coords;
coords.push_back(tileX);
coords.push_back(tileY);

return coords;
}

vector<int> carthesianToIsometric(int x, int y) {
vector<int> coords;

float isoX = (x - y) / 2,
isoY = (x + y) / 4;

coords.push_back(isoX);
coords.push_back(isoY);

return coords;
}

#include "Object.h"#include "Scene.h"
//...

И вот, результат WTF я получаю:

введите описание изображения здесь

Спасибо за чтение всего этого странного кода!

Редактировать :

Когда я меняюсь

tile.setPosition(sf::Vector2f(tile_x, tile_y));

в

tile.setPosition(sf::Vector2f(0, 0));

в updateMap() from scene.cpp:

введите описание изображения здесь

К сожалению, я не могу объяснить, почему. Может быть, это поможет вам понять проблему.

0

Решение

В случае, если кто-то сталкивается с той же проблемой:
Как предположил @Spectre, это была проблема функции sfml draw ().

http://en.sfml-dev.org/forums/index.php?topic=6903.0
Вам нужно использовать дисплей на sf::renderTexture после того, как вы очистили его.

0

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]