Sprite mapMaximSprite(mapMaximImg, 32, 64);
Entity mapMaxim;
mapMaxim.SetSprite(&mapMaximSprite);
- mapMaxim.Position() = Vector<float>(80, 160);
+ mapMaxim.Position() = Vector<float>(80, 128);
InitScreen screen(width, height);
#include "Tile.h"
#include "../graphics/Sprite.h"
+#include <stdexcept>
+
using geometry::Vector;
namespace map {
}
+
+const Tile &Area::TileAt(const geometry::Vector<int> &offset) const {
+ int tileIndex(offset.Y() * width + offset.X());
+ if (tileIndex < numTiles) {
+ return tiles[tileIndex];
+ } else {
+ throw std::out_of_range("tile index out of range");
+ }
+}
+
+
void Area::Render(SDL_Surface *dest, const graphics::Sprite *tileset, const Vector<int> &inOffset) const {
for (int i(0); i < numTiles; ++i) {
Vector<int> offset(
#include "fwd.h"
#include "../geometry/Vector.h"
-#include "../graphics/fwd.h"
+#include "../graphics/Sprite.h"
#include <SDL.h>
public:
int Width() const { return width; }
int Height() const { return numTiles / width + (numTiles % width ? 1 : 0); }
+ const Tile &TileAt(const geometry::Vector<int> &) const;
void Render(SDL_Surface *dest, const graphics::Sprite *tileset, const geometry::Vector<int> &offset) const;
bool Entity::TileLock(int width, int height) const {
Vector<int> tilePosition(
position.X() - (width / 2),
- position.Y() - height);
+ position.Y());
return (tilePosition.X() % width == 0) && (tilePosition.Y() % height == 0);
}
void Entity::Render(SDL_Surface *dest, const Vector<int> &offset) const {
+ // TODO: configurable sprite offsets
if (animation.Running()) {
- animation.DrawCenterBottom(dest, offset + position);
+ animation.DrawCenter(dest, offset + position);
} else {
- sprite->DrawCenterBottom(dest, offset + position, orientation);
+ sprite->DrawCenter(dest, offset + position, orientation);
}
}
const graphics::AnimationRunner &Animation() const { return animation; }
void SetOrientation(Orientation);
+ Orientation GetOrientation() const { return orientation; }
void SetSpeed(float);
bool TileLock(int width, int height) const;
#include "Area.h"
#include "../graphics/Sprite.h"
+#include <stdexcept>
+
using geometry::Vector;
namespace map {
}
+const Area &Map::AreaAt(const Vector<int> &offset) const {
+ if (numAreas > 0) {
+ Vector<int> tileOffset(offset.X() / tileset->Width(), offset.Y() / tileset->Height());
+ Vector<int> areaOffset(tileOffset.X() / areas[0].Width(), tileOffset.Y() / areas[0].Height());
+ int areaIndex(areaOffset.Y() * width + areaOffset.X());
+ if (areaIndex < numAreas) {
+ return areas[areaIndex];
+ }
+ }
+ throw std::out_of_range("area offset out of bounds");
+}
+
+const Tile &Map::TileAt(const Vector<int> &offset) const {
+ const Area &area(AreaAt(offset));
+ Vector<int> tileOffset((offset.X() / tileset->Width()) % area.Width(), (offset.Y() / tileset->Height()) % area.Height());
+ return area.TileAt(tileOffset);
+}
+
+
void Map::Render(SDL_Surface *dest, const Vector<int> &inOffset) const {
// TODO: skip invisible areas
for (int i(0); i < numAreas; ++i) {
public:
const graphics::Sprite *Tileset() const { return tileset; }
+ const Area &AreaAt(const geometry::Vector<int> &) const;
+ const Tile &TileAt(const geometry::Vector<int> &) const;
void Render(SDL_Surface *dest, const geometry::Vector<int> &offset) const;
#include "MapState.h"
#include "Map.h"
+#include "Tile.h"
#include "../app/Application.h"
#include "../app/Input.h"
if (!controlled) return;
if (!controlled->TileLock(map->Tileset()->Width(), map->Tileset()->Height())) return;
+ bool down(false);
if (input.IsDown(Input::PAD_UP)) {
controlled->SetOrientation(Entity::ORIENTATION_NORTH);
- controlled->SetSpeed(walkingSpeed);
+ down = true;
} else if (input.IsDown(Input::PAD_RIGHT)) {
controlled->SetOrientation(Entity::ORIENTATION_EAST);
- controlled->SetSpeed(walkingSpeed);
+ down = true;
} else if (input.IsDown(Input::PAD_DOWN)) {
controlled->SetOrientation(Entity::ORIENTATION_SOUTH);
- controlled->SetSpeed(walkingSpeed);
+ down = true;
} else if (input.IsDown(Input::PAD_LEFT)) {
controlled->SetOrientation(Entity::ORIENTATION_WEST);
- controlled->SetSpeed(walkingSpeed);
+ down = true;
+ }
+
+ if (down) {
+ const Tile &tile(map->TileAt(controlled->Position()));
+ bool blocked(false);
+ switch (controlled->GetOrientation()) {
+ case Entity::ORIENTATION_NORTH:
+ blocked = tile.BlocksNorth();
+ break;
+ case Entity::ORIENTATION_EAST:
+ blocked = tile.BlocksEast();
+ break;
+ case Entity::ORIENTATION_SOUTH:
+ blocked = tile.BlocksSouth();
+ break;
+ case Entity::ORIENTATION_WEST:
+ blocked = tile.BlocksWest();
+ break;
+ }
+ if (!blocked) {
+ controlled->SetSpeed(walkingSpeed);
+ } else {
+ controlled->SetSpeed(0.0f);
+ }
} else {
controlled->SetSpeed(0.0f);
}