Beispiel #1
0
// Get all neighbouring directions
RoadTile::Directions RoadTile::getNeighbouringDirections() {
    Directions dir;
    for (Tile* t : getNeighbours()) {
        dir.insert(Tile::calculateDirection(getTilePosition(), t->getTilePosition()));
    }
    return dir;
}
bool Route::Path::Find(s32 to, int limit)
{
    const int pathfinding = hero->GetLevelSkill(Skill::Secondary::PATHFINDING);
    const s32 from = hero->GetIndex();

    s32 cur = from;
    s32 alt = 0;
    s32 tmp = 0;
    std::map<s32, cell_t> list;
    std::map<s32, cell_t>::iterator it1 = list.begin();
    std::map<s32, cell_t>::iterator it2 = list.end();

    list[cur].cost_g = 0;
    list[cur].cost_t = 0;
    list[cur].parent = -1;
    list[cur].open   = 0;

    const Directions directions = Direction::All();
    clear();

    while(cur != to)
    {
	LocalEvent::Get().HandleEvents(false);
    	for(Directions::const_iterator
	    it = directions.begin(); it != directions.end(); ++it)
	{
    	    if(Maps::isValidDirection(cur, *it))
	    {
		tmp = Maps::GetDirectionIndex(cur, *it);

		if(list[tmp].open)
		{
		    const u32 costg = GetPenaltyFromTo(cur, tmp, *it, pathfinding);

		    // new
		    if(-1 == list[tmp].parent)
		    {
			if((list[cur].passbl & *it) ||
			   PassableFromToTile(*hero, cur, tmp, *it, to))
			{
			    list[cur].passbl |= *it;

			    list[tmp].direct = *it;
	    		    list[tmp].cost_g = costg;
			    list[tmp].parent = cur;
			    list[tmp].open   = 1;
			    list[tmp].cost_d = 50 * Maps::GetApproximateDistance(tmp, to);
	    		    list[tmp].cost_t = list[cur].cost_t + costg;
			}
		    }
		    // check alt
		    else
		    {
			if(list[tmp].cost_t > list[cur].cost_t + costg &&
			   ((list[cur].passbl & *it) || PassableFromToTile(*hero, cur, tmp, *it, to)))
			{
			    list[cur].passbl |= *it;

			    list[tmp].direct = *it;
			    list[tmp].parent = cur;
			    list[tmp].cost_g = costg;
			    list[tmp].cost_t = list[cur].cost_t + costg;
			}
		    }
    		}
	    }
	}

	list[cur].open = 0;

	it1 = list.begin();
	alt = -1;
	tmp = MAXU16;

	DEBUG(DBG_OTHER, DBG_TRACE, "route, from: " << cur);

	// find minimal cost
	for(; it1 != it2; ++it1) if((*it1).second.open)
	{
	    const cell_t & cell2 = (*it1).second;
#ifdef WITH_DEBUG
	    if(IS_DEBUG(DBG_OTHER, DBG_TRACE) && cell2.cost_g != MAXU16)
	    {
		int direct = Direction::Get(cur, (*it1).first);

		if(Direction::UNKNOWN != direct)
		{
		    VERBOSE("\t\tdirect: " << Direction::String(direct) <<
			    ", index: " << (*it1).first <<
			    ", cost g: " << cell2.cost_g <<
			    ", cost t: " << cell2.cost_t <<
			    ", cost d: " << cell2.cost_d);
		}
	    }
#endif

	    if(cell2.cost_t + cell2.cost_d < tmp)
	    {
    		tmp = cell2.cost_t + cell2.cost_d;
    		alt = (*it1).first;
	    }
	}

	// not found, and exception
	if(MAXU16 == tmp || -1 == alt) break;
#ifdef WITH_DEBUG
	else
	DEBUG(DBG_OTHER, DBG_TRACE, "select: " << alt);
#endif
	cur = alt;

	if(0 < limit && GetCurrentLength(list, cur) > limit) break;
    }

    // save path
    if(cur == to)
    {
	while(cur != from)
	{
	    push_front(Route::Step(list[cur].parent, list[cur].direct, list[cur].cost_g));
    	    cur = list[cur].parent;
	}
    }
    else
    {
	DEBUG(DBG_OTHER, DBG_TRACE, "not found" << ", from:" << from << ", to: " << to);
    }

    return !empty();
}
Beispiel #3
0
// Update texture and texture direction
void RoadTile::updateTile() {
    Directions dir = getNeighbouringDirections();
    int size = dir.size();
    // Find which directions exist
    bool east, west, south, north = false;
    east = (std::find(dir.begin(), dir.end(), Tile::EAST) != dir.end());
    south = (std::find(dir.begin(), dir.end(), Tile::SOUTH) != dir.end());
    west = (std::find(dir.begin(), dir.end(), Tile::WEST) != dir.end());
    north = (std::find(dir.begin(), dir.end(), Tile::NORTH) != dir.end());
    
    // Rotating
    if (size == 2) {
        // Strait
        if ((east && west) || (south && north)) {
            mSprite.setTexture(mTextureManager->getRoad_strait());
            if (south || north) mSprite.setRotation(90.0f);
            else mSprite.setRotation(0.0f);
        }
        // Turn
        else {
            mSprite.setTexture(mTextureManager->getRoad_turn());
            if (west && north) mSprite.setRotation(90.0f);
            else if (north && east) mSprite.setRotation(180.0f);
            else if (east && south) mSprite.setRotation(270.0f);
            else mSprite.setRotation(0.0f);
        }
    }
    // Three-way
    else if (size == 3) {
        mSprite.setTexture(mTextureManager->getRoad_threeWay());
        if (north && west && south) mSprite.setRotation(90.0f);
        else if (east && north && west) mSprite.setRotation(180.0f);
        else if (south && east && north) mSprite.setRotation(270.0f);
        else mSprite.setRotation(0.0f);
    }
    // Four-way
    else if (size == 4) {
        mSprite.setTexture(mTextureManager->getRoad_fourWay());
    }
    // Dead end
    else {
        mSprite.setTexture(mTextureManager->getRoad_blank());
        mSprite.setRotation(0.0f);
    }
}