Stilllegung des Forums
Das Forum wurde am 05.06.2023 nach über 20 Jahren stillgelegt (weitere Informationen und ein kleiner Rückblick).
Registrierungen, Anmeldungen und Postings sind nicht mehr möglich. Öffentliche Inhalte sind weiterhin zugänglich.
Das Team von spieleprogrammierer.de bedankt sich bei der Community für die vielen schönen Jahre.
Wenn du eine deutschsprachige Spieleentwickler-Community suchst, schau doch mal im Discord und auf ZFX vorbei!
Werbeanzeige
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
sf::Sprite tiles(tiletexture); // tiletexture ist ein PNG-File mit der Sammlung von den Texturen der einzelnen Tiles for(int i = 0; i < map.size(); i++) { for(int j = 0; j < map[i].size(); j++) { if(map[i][j] != sf::Vector2i(-1, -1)) { tiles.setPosition(j * 16 * 2,i * 16 * 2); tiles.setTextureRect(sf::IntRect(map[i][j].x * 16,map[i][j].y * 16, 16, 16)); tiles.setScale(2.0,2.0); window.draw(tiles); } } } |
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
for(int i = 0; i < colmap.size(); i++) { for(int j = 0; j < colmap[i].size(); j++) { sf::RectangleShape tile(sf::Vector2f(32,32)); tile.setPosition(j * 32, i * 32); if(player.getSprite().getGlobalBounds().intersects(tile.getGlobalBounds())) { if(colmap[i][j] == 1) { player.collision(); // void Player::collision funktioniert so, dass wenn zB. Taste 'A' für links gedrückt wird, break; // nach rechts 'geschoben' wird. } } } } |
Alter Hase
Beruf: Softwareentwickler (aktuell Web/Node); Freiberuflicher Google Proxy
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 |
// es gibt ein 2D Array (von mir aus auch std::vector) von Typ bool mit dem Namen tilemap // das ganze befindet sich in einer Klasse mit dem Namen Map. tilemap ist eine Membervariable von Map // die Membervariablen mit dem Namen tileWidth und tileHeight bestimmen die Breite und Höhe eines Tiles. In deinem Fall wäre das 32 // Die Parameter der Funktion sind Koordinaten in Pixeln, nicht in Tilelängen. Also wirkliche Positionsdaten bool Map::Collides(int x, int y) { return tilemap[x/tileWidth][x/tileWidth]; } |
sf::Vector2f ist ein Floating Point Vektor, wenn ich das jetzt aber richtig sehe benutzt du ihn zum Speichern von (Unsigned) Integer werten. Alle Werte die du ihm zuführst werden implizite in Floating Point Zahlen umgewandelt. Beim späteren Vergleich mit (Unsigned) Integer werten kann das zu Problemen führen. sf::Vector2i oder sf::Vector2u könnten angebrachter für deinen Bedarf sein.Ich schlage mich schon seit ein paar Tagen mit dem Problem rum, dass die Kollision auf meiner Tile-Map nicht funktioniert. Ich habe die Map szs. in zwei Teile eingeteilt. Einmal hab ich die Map an sich, die aus Zahlen wie zB. 3,42, die dann als eine 3 und eine 42 in einem std::vector<std::vector<sf::Vector2f>> namens map gespeichert werden.
Da hast du recht, ist mir auch schon aufgefallen. Aber mehr als eine Warnung im Compiler auszulösen, tut es nicht.sf::Vector2f ist ein Floating Point Vektor, wenn ich das jetzt aber richtig sehe benutzt du ihn zum Speichern von (Unsigned) Integer werten. Alle Werte die du ihm zuführst werden implizite in Floating Point Zahlen umgewandelt. Beim späteren Vergleich mit (Unsigned) Integer werten kann das zu Problemen führen. sf::Vector2i oder sf::Vector2u könnten angebrachter für deinen Bedarf sein.
C-/C++-Quelltext |
|
1 2 3 4 5 6 |
int Map::Collides(int x, int y) { if(player.getDirection() == 0) // 0 steht für oben, 1 für unten, 2 für links, 3 für rechts return colmap[y/tileHeight - 1][x/tileWidth]; // Ich hab X und Y vertauscht, weil es hier um einen std::vector in einem std::vector handelt //und das dann für alle Richtungen } |
C-/C++-Quelltext |
|
1 2 3 4 |
if(sf::Keyboard::isKeyPressed(sf::Keyboard::Up) && moveableUp) { player.move(0, speed * time.asMilliSeconds()); } |
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
#ifndef Map_h #define Map_h #include"player.h" #include<vector> #include<SFML/Graphics.hpp> class Map { public: Map(); void setCurrent(unsigned int current){this->current = current;} void draw(sf::RenderWindow& window, Player& player); void loadmap(); void loadcolmap(); int collides(int x, int y){return colmap[x/tilewidth][y/tileheight];} private: unsigned int current; sf::Sprite tiles; sf::Texture tiletexture; int tileheight, tilewidth; std::vector<std::vector<sf::Vector2i>> tilemap; std::vector<std::vector<int>> colmap; }; #endif |
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 |
#include"Map.h" #include"player.h" #include<SFML/Graphics.hpp> #include<fstream> #include<cctype> #include<sstream> Map::Map() { current = 1; tileheight = 32; tilewidth = 32; } void Map::loadmap() { std::ifstream openfile; switch(current) { case 1: openfile.open("map1.txt"); break; } tiletexture.loadFromFile("tileset.png"); tiles.setTexture(tiletexture); std::vector<sf::Vector2i> tempmap; tilemap.clear(); tempmap.clear(); if(openfile.is_open()) { //sf::Music music; //std::string location; //openfile >> location; //music.openFromFile(location); while(!openfile.eof()) { std::string str, value; std::getline(openfile,str); std::stringstream stream(str); while(std::getline(stream, value, ' ')) { if(value.length() > 0) { std::string xx = value.substr(0, value.find(',')); std::string yy = value.substr(value.find(',') + 1); int x, y, i, j; for(i = 0; i < xx.length(); i++) { if(!std::isdigit(xx[i])) break; } for(j = 0; j < yy.length(); j++) { if(!std::isdigit(yy[j])) break; } x = (i == xx.length() ? std::atoi(xx.c_str()) : -1); y = (j == yy.length() ? std::atoi(yy.c_str()) : -1); tempmap.push_back(sf::Vector2i(x,y)); } } if(tempmap.size() > 0) { tilemap.push_back(tempmap); tempmap.clear(); } } } } void Map::loadcolmap() { std::ifstream openfile; switch(current) { case 1: openfile.open("col1.txt"); break; } std::vector<int> tempmap; colmap.clear(); tempmap.clear(); if(openfile.is_open()) { while(!openfile.eof()) { std::string str, value; std::getline(openfile,str); std::stringstream stream(str); while(std::getline(stream, value, ' ')) { if(value.length() > 0) { int a = std::atoi(value.c_str()); tempmap.push_back(a); } } if(tempmap.size() > 0) { colmap.push_back(tempmap); tempmap.clear(); } } } } void Map::draw(sf::RenderWindow& window, Player& player) { window.clear(); for(int i = 0; i < tilemap.size(); i++) { for(int j = 0; j < tilemap[i].size(); j++) { if(tilemap[i][j] != sf::Vector2i(-1, -1)) { tiles.setPosition(j * 16 * 2,i * 16 * 2); tiles.setTextureRect(sf::IntRect(tilemap[i][j].x * 16, tilemap[i][j].y * 16, 16, 16)); tiles.setScale(2.0,2.0); window.draw(tiles); } } } window.draw(player.getSprite()); window.display(); } |
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
#ifndef player_h #define player_h #include<SFML/Graphics.hpp> #include<vector> class Player { public: Player(); void update(); void move(float X, float Y){sprite.move(X * time.asMilliseconds(), Y * time.asMilliseconds());} sf::Sprite getSprite(){return sprite;} sf::Vector2f topleft, topright, bottomleft, bottomright; private: float speed; sf::Clock clock, animationclock; sf::Vector2f direction; sf::Texture texture; sf::Time time; sf::Sprite sprite; }; #endif |
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 |
#include"player.h" #include<iostream> #include<algorithm> Player::Player() { texture.loadFromFile("ash.png"); direction = sf::Vector2f(0,0); animationclock.restart(); sprite.setTexture(texture); sprite.setPosition(300,300); speed = 0.1; } void Player::update() { topleft = sf::Vector2f(sprite.getPosition().x, sprite.getPosition().y); topright = sf::Vector2f(sprite.getPosition().x + 32, sprite.getPosition().y); bottomleft = sf::Vector2f(sprite.getPosition().x, sprite.getPosition().y + 32); bottomright = sf::Vector2f(sprite.getPosition().x + 32, sprite.getPosition().y + 32); //Controls time = clock.getElapsedTime(); if(sf::Keyboard::isKeyPressed) clock.restart(); if(sf::Keyboard::isKeyPressed(sf::Keyboard::W)) { sprite.move(0,- speed * time.asMilliseconds()); direction.y = 0; } else if(sf::Keyboard::isKeyPressed(sf::Keyboard::S)) { sprite.move(0, speed * time.asMilliseconds()); direction.y = 1; } else if(sf::Keyboard::isKeyPressed(sf::Keyboard::A)) { sprite.move(- speed * time.asMilliseconds(), 0); direction.y = 2; } else if(sf::Keyboard::isKeyPressed(sf::Keyboard::D)) { sprite.move(speed * time.asMilliseconds(), 0); direction.y = 3; } //Animation else if(sf::Keyboard::isKeyPressed) animationclock.restart(); if(animationclock.getElapsedTime() > sf::seconds(0.25)) { direction.x++; animationclock.restart(); if(direction.x == 3) direction.x = 0; } sprite.setTextureRect(sf::IntRect(direction.x * 32,direction.y * 32, 32, 32)); } |
C-/C++-Quelltext |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 |
#include<SFML/Graphics.hpp> #include<iostream> #include"player.h" #include"Map.h" int main() { Map map; sf::RenderWindow window(sf::VideoMode(640,480),"Pokémon"); Player player; while(window.isOpen()) { sf::Event gameevent; while(window.pollEvent(gameevent)) { switch(gameevent.type) { case sf::Event::Closed: window.close(); break; } } player.update(); map.loadmap(); map.loadcolmap(); map.draw(window, player); if(map.collides((int)player.topleft.y, (int)player.topleft.x) == 1) { player.move(0.1,0.1); } if(map.collides((int)player.topright.y, (int)player.topright.x) == 1) { player.move(-0.1,0.1); } if(map.collides((int)player.bottomleft.y, (int)player.bottomleft.x) == 1) { player.move(0.1,-0.1); } if(map.collides((int)player.bottomright.y, (int)player.bottomright.x) == 1) { player.move(-0.1,-0.1); } } return EXIT_SUCCESS; } |
Alter Hase
Beruf: Softwareentwickler (aktuell Web/Node); Freiberuflicher Google Proxy
Ich will ja nicht lästig sein. Aber ein Cast, dazu auch noch ein C-Cast in der Form ist selten eine gute Idee. Hier wird der Float Wert gerundet, und bei c/c++ wird immer abgerundet. So etwas kann zu durchaus sehr schwer zu findenden Laufzeitfehlern führen. Fatal wird dies aber im Zusammenhang der endlichen Genauigkeit von Float Werten. Es kann durchaus passieren, dass durch Operationen wie z.B. 10.0f / 2 zu 4.999…f wird. Bei deinem Cast wird dieser Wert zu einem Integer Wert von 4 und der Compiler meckert nicht mal.(int)player.topleft.y
Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von »H5::« (11.07.2013, 14:38)
Werbeanzeige