Esempio n. 1
0
void Chunk::PlaceTileAt(int x,int y, int type) {
	GetTileAt(x, y)->type = type;
	for (int i = x - 1; i <= x + 1; i++) {
		for (int j = y - 1; j <= y + 1; j++) {
			Tile* tilePtr = GetTileAt(i, j);
			CheckSurroundings(tilePtr);
		}
	}
}
Esempio n. 2
0
// See if the tile located at a position is a door and also needs
// to be oriented in a certain way
// If there are walls or doors in the neighbourhood, they can force a certain
// orientation of the door
static int HasDoorOrientedAt(Mission *m, Vec2i pos,int isHorizontal)
{
	unsigned short tile = GetTileAt(m, pos);
	if (tile != MAP_DOOR)
	{
		return 0;
	}
	// Check for walls and doors that force the orientation of the door
	if (GetTileAt(m, Vec2iNew(pos.x - 1, pos.y)) == MAP_WALL ||
		GetTileAt(m, Vec2iNew(pos.x - 1, pos.y)) == MAP_DOOR ||
		GetTileAt(m, Vec2iNew(pos.x + 1, pos.y)) == MAP_WALL ||
		GetTileAt(m, Vec2iNew(pos.x + 1, pos.y)) == MAP_DOOR)
	{
		// There is a horizontal door
		return isHorizontal;
	}
	else if (GetTileAt(m, Vec2iNew(pos.x, pos.y - 1)) == MAP_WALL ||
		GetTileAt(m, Vec2iNew(pos.x, pos.y - 1)) == MAP_DOOR ||
		GetTileAt(m, Vec2iNew(pos.x, pos.y + 1)) == MAP_WALL ||
		GetTileAt(m, Vec2iNew(pos.x, pos.y + 1)) == MAP_DOOR)
	{
		// There is a vertical door
		return !isHorizontal;
	}
	// There is a door but it is free to be oriented in any way
	return 0;
}
Esempio n. 3
0
vector<Entity*> GameView::GetEntitiesInRadius(const Vector2& in_pos, float in_radius)
{
    vector<Entity*> res;
    Tile* tile = GetTileAt(in_pos);
    if (tile)
    {
        FillVectorWithEntitiesInRadius(tile, in_pos, in_radius, res);
    }

    // get all the tiles around it
    tile = GetTileAt(in_pos + Vector2(-1,0));
    if (tile)
    {
        FillVectorWithEntitiesInRadius(tile, in_pos, in_radius, res);
    }

    tile = GetTileAt(in_pos + Vector2(-1, -1));
    if (tile)
    {
        FillVectorWithEntitiesInRadius(tile, in_pos, in_radius, res);
    }

    tile = GetTileAt(in_pos + Vector2(0, -1));
    if (tile)
    {
        FillVectorWithEntitiesInRadius(tile, in_pos, in_radius, res);
    }

    tile = GetTileAt(in_pos + Vector2(1, -1));
    if (tile)
    {
        FillVectorWithEntitiesInRadius(tile, in_pos, in_radius, res);
    }

    tile = GetTileAt(in_pos + Vector2(1, 0));
    if (tile)
    {
        FillVectorWithEntitiesInRadius(tile, in_pos, in_radius, res);
    }

    tile = GetTileAt(in_pos + Vector2(1, 1));
    if (tile)
    {
        FillVectorWithEntitiesInRadius(tile, in_pos, in_radius, res);
    }

    tile = GetTileAt(in_pos + Vector2(0, 1));
    if (tile)
    {
        FillVectorWithEntitiesInRadius(tile, in_pos, in_radius, res);
    }

    tile = GetTileAt(in_pos + Vector2(-1, 1));
    if (tile)
    {
        FillVectorWithEntitiesInRadius(tile, in_pos, in_radius, res);
    }
    return res;
}
Esempio n. 4
0
bool MissionTrySetTile(Mission *m, Vec2i pos, unsigned short tile)
{
	if (pos.x < 0 || pos.x >= m->Size.x || pos.y < 0 || pos.y >= m->Size.y)
	{
		return false;
	}
	CASSERT(m->Type == MAPTYPE_STATIC, "cannot set tile for map type");
	switch (tile)
	{
	case MAP_WALL:
		// Check that there are no incompatible doors
		if (HasDoorOrientedAt(m, Vec2iNew(pos.x - 1, pos.y), 0) ||
			HasDoorOrientedAt(m, Vec2iNew(pos.x + 1, pos.y), 0) ||
			HasDoorOrientedAt(m, Vec2iNew(pos.x, pos.y - 1), 1) ||
			HasDoorOrientedAt(m, Vec2iNew(pos.x, pos.y + 1), 1))
		{
			// Can't place this wall
			return false;
		}
		break;
	case MAP_DOOR:
		{
			// Check that there is a clear passage through this door
			int isHClear =
				IsClear(GetTileAt(m, Vec2iNew(pos.x - 1, pos.y))) &&
				IsClear(GetTileAt(m, Vec2iNew(pos.x + 1, pos.y)));
			int isVClear =
				IsClear(GetTileAt(m, Vec2iNew(pos.x, pos.y - 1))) &&
				IsClear(GetTileAt(m, Vec2iNew(pos.x, pos.y + 1)));
			if (!isHClear && !isVClear)
			{
				return false;
			}
			// Check that there are no incompatible doors
			if (HasDoorOrientedAt(m, Vec2iNew(pos.x - 1, pos.y), 0) ||
				HasDoorOrientedAt(m, Vec2iNew(pos.x + 1, pos.y), 0) ||
				HasDoorOrientedAt(m, Vec2iNew(pos.x, pos.y - 1), 1) ||
				HasDoorOrientedAt(m, Vec2iNew(pos.x, pos.y + 1), 1))
			{
				// Can't place this door
				return false;
			}
		}
		break;
	}
	const int idx = pos.y * m->Size.x + pos.x;
	*(unsigned short *)CArrayGet(&m->u.Static.Tiles, idx) = tile;
	return true;
}
Esempio n. 5
0
void GameView::SpawnMonster()
{
    if (Monster::count >= MAX_MONSTER_COUNT) return;
    for (int tries = 0; tries < 10; ++tries)
    {
        int side = onut::randi() % 4;
        Vector2 spawnPos;
        switch (side)
        {
            case 0:
                spawnPos = onut::rand2f(Vector2::Zero, Vector2((float)m_pTilemap->getWidth(), 2.5f));
                break;
            case 1:
                spawnPos = onut::rand2f(Vector2::Zero, Vector2(2.5f, (float)m_pTilemap->getHeight()));
                break;
            case 2:
                spawnPos = onut::rand2f(Vector2((float)m_pTilemap->getWidth() - 2.5f, 0.f), Vector2(Vector2((float)m_pTilemap->getWidth(), (float)m_pTilemap->getHeight())));
                break;
            case 3:
                spawnPos = onut::rand2f(Vector2(0.f, (float)m_pTilemap->getHeight() - 2.5f), Vector2(Vector2((float)m_pTilemap->getWidth(), (float)m_pTilemap->getHeight())));
                break;
        }
        spawnPos.x = std::round(spawnPos.x) + .5f;
        spawnPos.y = std::round(spawnPos.y) + .5f;
        auto pTile = GetTileAt(spawnPos);
        if (!pTile) continue;
        if (!pTile->isOccupied)
        {
            auto pMonster = new Monster(MonsterType::CRAWLER, this, spawnPos);
            AddEntity(pMonster);
            break;
        }
    }
}
Esempio n. 6
0
void Chunk::DigTileAt(int x,int y) {
	RemoveTileAt(x, y);
	for (int i = x - 1; i <= x + 1; i++) {
		for (int j = y - 1; j <= y + 1; j++) {
			Tile* tilePtr = GetTileAt(i, j);
			CheckSurroundings(tilePtr);
		}
	}
}
Esempio n. 7
0
void GameView::OnEntityMoved(Entity* pEntity)
{
    m_pGameLayer->Detach(pEntity);
    m_pGameLayer->Attach(pEntity, (int)(pEntity->GetPosition().y * 16.f));
    auto pTile = GetTileAt(pEntity->GetPosition());
    if (pTile)
    {
        pTile->RegisterEntity(pEntity);
    }
}
Esempio n. 8
0
void GameView::GenerateMap()
{
    Vector2 mapCenter((float)m_pTilemap->getWidth() * .5f, (float)m_pTilemap->getHeight() * .5f);

    m_pStockpile = new Stockpile(this, m_pTilemap->getWidth() / 2 + 1, m_pTilemap->getHeight() / 2 - 4);
    AddEntity(m_pStockpile);

    // Spawn a bunch of trees
    for (int i = 0; i < TREE_DENSITY; ++i)
    {
        auto center = onut::rand2f(Vector2::Zero, Vector2((float)m_pTilemap->getWidth(), (float)m_pTilemap->getHeight()));
        int count = onut::randi(2, 12);
        for (int j = 0; j < count; ++j)
        {
            auto pos = center += onut::rand2f(Vector2(-3), Vector2(3));
            pos.x = std::round(pos.x) + .5f;
            pos.y = std::round(pos.y) + .5f;
            if (pos.x >= mapCenter.x - 3 && pos.y >= mapCenter.y - 3 &&
                pos.x <= mapCenter.x + 3 && pos.y <= mapCenter.y + 3) continue;
            if (pos.x < 1.f || pos.y < 1.f || pos.x >(float)m_pTilemap->getWidth() - 1.f || pos.y >(float)m_pTilemap->getHeight() - 1.f) continue;
            auto pTile = GetTileAt(pos);
            if (!pTile) continue;
            if (pTile->isOccupied) continue;
            pTile->isOccupied = true;
            auto pTree = new Tree(this, pos);
            AddEntity(pTree);
        }
    }

    // Spawn a bunch of rockz
    for (int i = 0; i < ROCK_DENSITY; ++i)
    {
        auto center = onut::rand2f(Vector2::Zero, Vector2((float)m_pTilemap->getWidth(), (float)m_pTilemap->getHeight()));
        int count = onut::randi(2, 6);
        for (int j = 0; j < count; ++j)
        {
            auto pos = center += onut::rand2f(Vector2(-3), Vector2(3));
            pos.x = std::round(pos.x) + .5f;
            pos.y = std::round(pos.y) + .5f;
            if (pos.x >= mapCenter.x - 3 && pos.y >= mapCenter.y - 3 &&
                pos.x <= mapCenter.x + 3 && pos.y <= mapCenter.y + 3) continue;
            if (pos.x < 1.f || pos.y < 1.f || pos.x >(float)m_pTilemap->getWidth() - 1.f || pos.y >(float)m_pTilemap->getHeight() - 1.f) continue;
            auto pTile = GetTileAt(pos);
            if (!pTile) continue;
            if (pTile->isOccupied) continue;
            pTile->isOccupied = true;
            auto pRock = new Rock(this, pos);
            AddEntity(pRock);
        }
    }

    for (int i = 0; i < m_pTilemap->getWidth(); ++i)
    {
        GetTileAt(i, 0)->isOccupied = true;
        GetTileAt(0, i)->isOccupied = true;
        GetTileAt(i, m_pTilemap->getHeight() - 1)->isOccupied = true;
        GetTileAt(m_pTilemap->getWidth() - 1, i)->isOccupied = true;
    }
}
Esempio n. 9
0
int Chunk::GetItemFromTile(int x,int y) {
	switch (GetTileAt(x,y)->type) {
	case Type::DIRT:
	case Type::GRASS:
		return 2;
		break;
	case Type::COBBLE:
		return 3;
		break;
	default:
		return 0;
	}
}
Esempio n. 10
0
void GameView::ClearEntities()
{
    for (size_t i = 0; i < m_entitiesToKill.size(); ++i)
    {
        for (auto it = m_scarecrows.begin(); it != m_scarecrows.end();)
        {
            if ((*it) == m_entitiesToKill[i])
            {
                it = m_scarecrows.erase(it);
                break;
            }
            else
            {
                ++it;
            }
        }
        for (auto it = m_entities.begin(); it != m_entities.end();)
        {
            if ((*it) == m_entitiesToKill[i])
            {
                it = m_entities.erase(it);
                DeleteNode(m_entitiesToKill[i]);
                break;
            }
            else
            {
                ++it;
            }
        }
    }
    m_entitiesToKill.clear();

    for (auto pEntity : m_entitiesToAdd)
    {
        m_pGameLayer->Attach(pEntity, (int)(pEntity->GetPosition().y * 16.f));
        m_entities.push_back(pEntity);
        auto pTile = GetTileAt(pEntity->GetPosition());
        if (pTile)
        {
            pTile->RegisterEntity(pEntity);
        }
        if (dynamic_cast<Scarecrow*>(pEntity))
        {
            m_scarecrows.push_back(pEntity);
        }
    }
    m_entitiesToAdd.clear();
}
Esempio n. 11
0
void Chunk::CheckSurroundings(Tile* currentTilePtr) {
	if (currentTilePtr == nullptr) return;
	bool left, right, top, bottom;

	left = CheckTileToAir(currentTilePtr,GetTileAt(currentTilePtr->x - 1, currentTilePtr->y));
	right = CheckTileToAir(currentTilePtr,GetTileAt(currentTilePtr->x + 1, currentTilePtr->y));
	top = CheckTileToAir(currentTilePtr,GetTileAt(currentTilePtr->x, currentTilePtr->y - 1));
	bottom = CheckTileToAir(currentTilePtr,GetTileAt(currentTilePtr->x, currentTilePtr->y + 1));

	currentTilePtr->air = BoolToInt(left, right, top, bottom);

	left = CheckTileToBackgroundAir(currentTilePtr, GetTileAt(currentTilePtr->x - 1, currentTilePtr->y));
	right = CheckTileToBackgroundAir(currentTilePtr, GetTileAt(currentTilePtr->x + 1, currentTilePtr->y));
	top = CheckTileToBackgroundAir(currentTilePtr, GetTileAt(currentTilePtr->x, currentTilePtr->y - 1));
	bottom = CheckTileToBackgroundAir(currentTilePtr, GetTileAt(currentTilePtr->x, currentTilePtr->y + 1));

	currentTilePtr->noBackround = BoolToInt(left, right, top, bottom);
	
}
Esempio n. 12
0
void TileSetPanel::OnLeftButtonPressed(wxMouseEvent& event)
{
    if (!m_tileset || m_tileset->IsDirty())
        return;

    wxPoint mousePos = CalcUnscrolledPosition(event.GetPosition());

    //Select the tile
    int selectedCol, selectedRow;
    GetTileAt(mousePos, selectedCol, selectedRow);
    if (selectedCol >= m_tileset->GetColumnsCount() || selectedRow >= m_tileset->GetRowsCount())
        return;
    m_selectedCol = selectedCol;
    m_selectedRow = selectedRow;

    //Send the event
    TileSelectionEvent newEvent(TILE_SELECTION_CHANGED, GetId(), m_tileset->GetTileIDFromCell(m_selectedCol, m_selectedRow));
    newEvent.SetEventObject(this);
    ProcessWindowEvent(newEvent);

    Refresh();
}
Esempio n. 13
0
// Utility: returns true is the tile is walkable
bool j1PathFinding::IsWalkable(const iPoint& pos) const
{
	uchar t = GetTileAt(pos);
	return t != INVALID_WALK_CODE && t > 0;
}
Esempio n. 14
0
void TileMapPanel::OnMouseEvent(wxMouseEvent &event)
{
    if(!m_tilemap || !m_tileset)
        return;

    //Get the current tile position (column and row)
    int currentColumn, currentRow;
    wxPoint mousePos = CalcUnscrolledPosition(event.GetPosition());
    GetTileAt(mousePos, currentColumn, currentRow);

    if(currentColumn >= m_tilemap->GetColumnsCount() || currentRow >= m_tilemap->GetRowsCount())
        return; //Stop if the position is out of range

    if(m_insertionMode == PencilMode)
    {
        if(event.GetEventType() == wxEVT_LEFT_DOWN || event.GetEventType() == wxEVT_RIGHT_DOWN || event.GetEventType() == wxEVT_MOTION)
        {
            if(event.LeftIsDown()) //Left mouse button pressed
            {
                //Add a tile to the current position (only if the tile has not been set before)
                if(m_tilemap->GetTile(m_mapCurrentLayer, currentColumn, currentRow) != m_tileToBeInserted)
                    m_commandProcessor.Submit(new ChangeTileCommand(*m_tilemap, m_mapCurrentLayer, currentColumn, currentRow, m_tileToBeInserted));
                Refresh();
            }
            else if(event.RightIsDown())
            {
                //Remove the tile
                if(m_tilemap->GetTile(m_mapCurrentLayer, currentColumn, currentRow) != m_tileToBeInserted)
                    m_commandProcessor.Submit(new ChangeTileCommand(*m_tilemap, m_mapCurrentLayer, currentColumn, currentRow, -1));
                Refresh();
            }
        }
    }
    else if(m_insertionMode == RectangleMode)
    {
        if(event.GetEventType() == wxEVT_LEFT_DOWN || event.GetEventType() == wxEVT_RIGHT_DOWN)
        {
            m_isDrawingRectangle = true;
            m_beginCol = m_endCol = currentColumn;
            m_beginRow = m_endRow = currentRow;

            Update();
        }
        else if(event.GetEventType() == wxEVT_MOTION)
        {
            m_endCol = currentColumn;
            m_endRow = currentRow;
            Update();
        }
        else if(event.GetEventType() == wxEVT_LEFT_UP)
        {
            m_endCol = currentColumn;
            m_endRow = currentRow;
            m_isDrawingRectangle = false;

            m_commandProcessor.Submit(new ChangeTileCommand(*m_tilemap, m_mapCurrentLayer, std::min(m_beginCol, m_endCol), 
                                                                                           std::min(m_beginRow, m_endRow), 
                                                                                           std::max(m_beginCol, m_endCol), 
                                                                                           std::max(m_beginRow, m_endRow), 
                                                                                           m_tileToBeInserted));

            Update();
        }
        else if(event.GetEventType() == wxEVT_RIGHT_UP)
        {
            m_endCol = currentColumn;
            m_endRow = currentRow;
            m_isDrawingRectangle = false;

            m_commandProcessor.Submit(new ChangeTileCommand(*m_tilemap, m_mapCurrentLayer, std::min(m_beginCol, m_endCol), 
                                                                                           std::min(m_beginRow, m_endRow), 
                                                                                           std::max(m_beginCol, m_endCol), 
                                                                                           std::max(m_beginRow, m_endRow), 
                                                                                           -1));

            Update();
        }
    }
    else if(m_insertionMode == FillMode)
    {
        if(event.GetEventType() == wxEVT_LEFT_DOWN)
        {
            m_commandProcessor.Submit(new FloodFillCommand(*m_tilemap, m_mapCurrentLayer, currentColumn, currentRow, m_tileToBeInserted));

            Update();
        }
    }
}
Esempio n. 15
0
Tile *GameView::GetTileAt(const Vector2& position) const
{
    auto x = (int)position.x;
    auto y = (int)position.y;
    return GetTileAt(x, y);
}