/** * Triangles * Copyright (C) 2016 POSITIVE MENTAL ATTITUDE * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, version 3 of the License. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "Foreground.hpp" #include #include Foreground::~Foreground() { for(unsigned i = 0; i < _sprites.size(); ++i) _sprites[i].clear(); _sprites.clear(); _tiles.clear(); } const sf::Vector2u Foreground::getSize() const { return {_tileCount.x * _tileSize, _tileCount.y * _tileSize}; } unsigned const Foreground::tileAlpha(unsigned x, unsigned y, unsigned pixelX, unsigned pixelY) { return _tiles[y * _tileCount.x + x].first.getPixel(pixelX, pixelY).a; } void Foreground::reloadFromTile(int x, int y, bool neighbouring) { if(x < 0 or y < 0 or x >= (int)_tileCount.x or y >= (int)_tileCount.y) return; if(neighbouring) { for(int i = -1; i <= 1; ++i) { if(x + i < 0 or x + i >= (int)_tileCount.x) continue; for(int j = -1; j <= 1; ++j) { if(y + j < 0 or y + j >= (int)_tileCount.y) continue; unsigned id = (y + j) * _tileCount.x + (x + i); _tiles[id].second.loadFromImage(_tiles[id].first); } } } else { unsigned id = y * _tileCount.x + x; _tiles[id].second.loadFromImage(_tiles[id].first); } } void Foreground::reloadFromPixel(int x, int y, bool neighbouring) { reloadFromTile((x / _tileSize), (y / _tileSize), neighbouring); } bool Foreground::destroy(unsigned x, unsigned y) { if((x / _tileSize) < 0 or (y / _tileSize) < 0 or (x / _tileSize) >= _tileCount.x or (y / _tileSize) >= _tileCount.y) return true; unsigned id = ((y / _tileSize) * _tileCount.x) + (x / _tileSize); x %= _tileSize; y %= _tileSize; int a = _tiles[id].first.getPixel(x, y).a; if(a > 0) { _tiles[id].first.setPixel(x, y, sf::Color::Transparent); return true; } else return false; } const unsigned Foreground::getTileSize() const { return _tileSize; } void Foreground::create(sf::Image& foreground, sf::Image& map) { _tileSize = 512; _position.x = 0; _position.y = 0; _tileCount.x = std::ceil(static_cast(map.getSize().x) / _tileSize); _tileCount.y = std::ceil(static_cast(map.getSize().y) / _tileSize); _tiles.clear(); _tiles.resize(_tileCount.x * _tileCount.y); _sprites.resize(_tileCount.x); for(unsigned i = 0; i < _tileCount.x; ++i) _sprites[i].resize(_tileCount.y); for(unsigned i = 0; i < _tiles.size(); ++i) std::get<0>(_tiles[i]).create(_tileSize, _tileSize, sf::Color::Yellow); for(unsigned i = 0; i < _tileCount.x * _tileSize; ++i) for(unsigned j = 0; j < _tileCount.y * _tileSize; ++j) { sf::Color color = foreground.getPixel(i % foreground.getSize().x, j % foreground.getSize().y); std::get<0>(_tiles[j / _tileSize * _tileCount.x + i / _tileSize]) .setPixel(i % _tileSize, j % _tileSize, sf::Color(color.r, color.g, color.b, i < map.getSize().x and j < map.getSize().y ? 255 - map.getPixel(i, j).r : 255)); } for(unsigned i = 0; i < _tiles.size(); ++i) { std::get<1>(_tiles[i]).loadFromImage(std::get<0>(_tiles[i])); _sprites[i % _tileCount.x][i / _tileCount.x].setTexture(std::get<1>(_tiles[i])); _sprites[i % _tileCount.x][i / _tileCount.x].setPosition((i % _tileCount.x) * _tileSize, (i / _tileCount.x) * _tileSize); //_sprites[i % _tileCount.x][i / _tileCount.x].setColor(sf::Color(rand() % 256,rand() % 256,rand() % 256, 255)); //Debug //std::get<2>(_tiles[i]).setTexture(std::get<1>(_tiles[i])); //std::get<2>(_tiles[i]).setPosition((i % _tileCount.x) * _tileSize, (i / _tileCount.x) * _tileSize); } } void Foreground::create(std::string foreground, std::string map) { sf::Image image1, image2; image1.loadFromFile(foreground); image2.loadFromFile(map); create(image1, image2); } void Foreground::setResolution(sf::Vector2u resolution) { sf::Vector2f temp; temp.x = static_cast(resolution.x) / static_cast(_tileSize); temp.y = static_cast(resolution.y) / static_cast(_tileSize); _renderCount = sf::Vector2u(std::ceil(temp.x) + 1, std::ceil(temp.y) + 1); } void Foreground::setPosition(sf::Vector2f position) { _position.x = position.x >= 0 ? position.x : 0; _position.y = position.y >= 0 ? position.y : 0; } void Foreground::draw(sf::RenderTarget& target, sf::RenderStates states) const { unsigned x = _position.x / _tileSize, y = _position.y / _tileSize; for(unsigned i = 0; i < _renderCount.x; ++i) for(unsigned j = 0; j < _renderCount.y; ++j) if(i + x < _tileCount.x and j + y < _tileCount.y) target.draw(_sprites[i + x][j + y], states); }