Exemplo n.º 1
0
sf::Vector2i coordsToRelative(sf::Vector2i const& coords)
{
    sf::Vector2i c;
    c.x  = coords.x % getLayerSize().x;
    c.y  = coords.y % getLayerSize().y;
    if (c.x < 0)
    {
        c.x += getLayerSize().x;
    }
    if (c.y < 0)
    {
        c.y += getLayerSize().y;
    }
    return c;
}
Exemplo n.º 2
0
//------------------------------------------------------------------
//
// TMXOrthoTest4New
//
//------------------------------------------------------------------
TMXOrthoTest4New::TMXOrthoTest4New()
{
    auto map = cocos2d::experimental::TMXTiledMap::create("TileMaps/orthogonal-test4.tmx");
    addChild(map, 0, kTagTileMap);
    
    Size CC_UNUSED s1 = map->getContentSize();
    CCLOG("ContentSize: %f, %f", s1.width,s1.height);
    
    map->setAnchorPoint(Vec2(0, 0));

    auto layer = map->getLayer("Layer 0");
    auto s = layer->getLayerSize();
    
    Sprite* sprite;
    sprite = layer->getTileAt(Vec2(0,0));
    sprite->setScale(2);
    sprite = layer->getTileAt(Vec2(s.width-1,0));
    sprite->setScale(2);
    sprite = layer->getTileAt(Vec2(0,s.height-1));
    sprite->setScale(2);
    sprite = layer->getTileAt(Vec2(s.width-1,s.height-1));
    sprite->setScale(2);

    schedule( CC_SCHEDULE_SELECTOR(TMXOrthoTest4New::removeSprite), 2 );

}
Exemplo n.º 3
0
//------------------------------------------------------------------
//
// TMXOrthoTest4
//
//------------------------------------------------------------------
TMXOrthoTest4::TMXOrthoTest4()
{
    auto map = TMXTiledMap::create("TileMaps/orthogonal-test4.tmx");
    addChild(map, 0, kTagTileMap);
    
    Size CC_UNUSED s1 = map->getContentSize();
    CCLOG("ContentSize: %f, %f", s1.width,s1.height);

    SpriteBatchNode* child = nullptr;
    
    auto& children = map->getChildren();
    
    for(const auto &node : children) {
        child = static_cast<SpriteBatchNode*>(node);
        child->getTexture()->setAntiAliasTexParameters();
    }
    
    map->setAnchorPoint(Vec2(0, 0));

    auto layer = map->getLayer("Layer 0");
    auto s = layer->getLayerSize();
    
    Sprite* sprite;
    sprite = layer->getTileAt(Vec2(0,0));
    sprite->setScale(2);
    sprite = layer->getTileAt(Vec2(s.width-1,0));
    sprite->setScale(2);
    sprite = layer->getTileAt(Vec2(0,s.height-1));
    sprite->setScale(2);
    sprite = layer->getTileAt(Vec2(s.width-1,s.height-1));
    sprite->setScale(2);

    schedule( schedule_selector(TMXOrthoTest4::removeSprite), 2 );

}
Exemplo n.º 4
0
void HelloWorld::createMapAndGetTile()
{
    auto mapnotchange = TMXTiledMap::create("orthogonal-test4.tmx");
    addChild(mapnotchange, 0, 1);
    mapnotchange->setPosition(50,240);
    
    auto map = TMXTiledMap::create("orthogonal-test4.tmx");
    addChild(map, 0, 2);
    map->setPosition(570,240);
    
    SpriteBatchNode* child = nullptr;
    
    auto& children = map->getChildren();
    
    for(const auto &node : children) {
        child = static_cast<SpriteBatchNode*>(node);
        child->getTexture()->setAntiAliasTexParameters();
    }
    
    map->setAnchorPoint(Point(0, 0));
    
    auto layer = map->getLayer("Layer 0");
    auto s = layer->getLayerSize();
    
    Sprite* sprite;
    sprite = layer->getTileAt(Point(0,0));
    sprite->setScale(2);
    sprite = layer->getTileAt(Point(s.width-1,0));
    sprite->setScale(2);
    sprite = layer->getTileAt(Point(0,s.height-1));
    sprite->setScale(2);
    sprite = layer->getTileAt(Point(s.width-1,s.height-1));
    sprite->setScale(2);
}
Exemplo n.º 5
0
sf::Vector2i coordsToChunk(sf::Vector2i const& coords)
{
    sf::Vector2i c;
    if (getLayerSize() != sf::Vector2i(0,0))
    {
        c.x = coords.x / getLayerSize().x;
        c.y = coords.y / getLayerSize().y;
        if (coords.x < 0)
        {
            c.x--;
        }
        if (coords.y < 0)
        {
            c.y--;
        }
    }
    return c;
}
Exemplo n.º 6
0
void TMXOrthoTest4::removeSprite(float dt)
{
    unschedule(schedule_selector(TMXOrthoTest4::removeSprite));

    auto map = static_cast<TMXTiledMap*>( getChildByTag(kTagTileMap) );
    auto layer = map->getLayer("Layer 0");
    auto s = layer->getLayerSize();

    auto sprite = layer->getTileAt( Point(s.width-1,0) );
    layer->removeChild(sprite, true);
}
Exemplo n.º 7
0
	void update()
	{
		const auto& renderers = getRenderers();
		for(const auto& renderer : renderers)
		{
			for(const auto input : renderer->getInputDatas())
				input->updateIfDirty();
			renderer->updateIfDirty();
		}

		auto renderSize = getLayerSize();
		int w = renderSize.width(), h = renderSize.height();

		if(!m_renderFrameBuffer || m_renderFrameBuffer.size() != renderSize)
		{
			graphics::FramebufferFormat format;
			format.samples = 16;
			m_renderFrameBuffer = graphics::Framebuffer(renderSize, format);
			m_displayFrameBuffer = graphics::Framebuffer(renderSize);

			// Setting the image Data to the display Fbo
			m_image.getAccessor()->setFbo(m_displayFrameBuffer);
		}

		m_renderFrameBuffer.bind();
		
		glViewport(0, 0, w, h);
		auto& mvp = getMVPMatrix(); // Modify the matrix that will be used by the renderers
		mvp.ortho(0, static_cast<float>(w), static_cast<float>(h), 0, -10.f, 10.f);

		glClearColor(0, 0, 0, 0);
		glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

		glEnable(GL_BLEND);
		glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);

		for(auto iter = renderers.rbegin(); iter != renderers.rend(); ++iter)
		{
			auto renderer = *iter;
			helper::ScopedEvent log(helper::event_render, renderer);
			renderer->render();
			renderer->cleanDirty();
		}

		glDisable(GL_BLEND);

		m_renderFrameBuffer.release();

		auto acc = m_image.getAccessor();
		graphics::RectInt area(0, 0, renderSize.width(), renderSize.height());
		graphics::Framebuffer::blitFramebuffer(*acc->getFbo(), area, m_renderFrameBuffer, area);
	}
Exemplo n.º 8
0
void TMXReadWriteTest::removeTiles(float dt)
{
    unschedule(schedule_selector(TMXReadWriteTest::removeTiles));

    auto map = (TMXTiledMap*)getChildByTag(kTagTileMap);
    auto layer = (TMXLayer*)map->getChildByTag(0);
    auto s = layer->getLayerSize();

    for( int y=0; y< s.height; y++ ) 
    {
        layer->removeTileAt( Vec2(5.0, (float)y) );
    }
}
Exemplo n.º 9
0
void TMXReadWriteTestNew::removeTiles(float dt)
{
    unschedule(CC_SCHEDULE_SELECTOR(TMXReadWriteTestNew::removeTiles));

    auto map = (cocos2d::experimental::TMXTiledMap*)getChildByTag(kTagTileMap);
    auto layer = (cocos2d::experimental::TMXLayer*)map->getChildByTag(0);
    auto s = layer->getLayerSize();

    for( int y=0; y< s.height; y++ ) 
    {
        layer->removeTileAt( Vec2(5.0, (float)y) );
    }
}
Exemplo n.º 10
0
void TMXReadWriteTestNew::repaintWithGID(float dt)
{
//    unschedule:_cmd);
    
    auto map = (cocos2d::experimental::TMXTiledMap*)getChildByTag(kTagTileMap);
    auto layer = (cocos2d::experimental::TMXLayer*)map->getChildByTag(0);
    
    auto s = layer->getLayerSize();
    for( int x=0; x<s.width;x++) 
    {
        int y = (int)s.height-1;
        unsigned int tmpgid = layer->getTileGIDAt( Vec2((float)x, (float)y) );
        layer->setTileGID(tmpgid+1, Vec2((float)x, (float)y));
    }
}
Exemplo n.º 11
0
void TMXOrthoTest4New::removeSprite(float dt)
{
    unschedule(CC_SCHEDULE_SELECTOR(TMXOrthoTest4New::removeSprite));

    auto map = static_cast<cocos2d::experimental::TMXTiledMap*>( getChildByTag(kTagTileMap) );
    auto layer = map->getLayer("Layer 0");
    auto s = layer->getLayerSize();

    auto sprite = layer->getTileAt( Vec2(s.width-1,0) );
    auto sprite2 = layer->getTileAt(Vec2(s.width-1, s.height-1));
    layer->removeChild(sprite, true);
    auto sprite3 = layer->getTileAt(Vec2(2, s.height-1));
    layer->removeChild(sprite3, true);
    layer->removeChild(sprite2, true);
}
Exemplo n.º 12
0
void TMXReadWriteTestNew::updateCol(float dt)
{    
    auto map = (cocos2d::experimental::TMXTiledMap*)getChildByTag(kTagTileMap);
    auto layer = (cocos2d::experimental::TMXLayer*)map->getChildByTag(0);

    ////----CCLOG("++++atlas quantity: %d", layer->textureAtlas()->getTotalQuads());
    ////----CCLOG("++++children: %d", layer->getChildren()->count() );
 

    auto s = layer->getLayerSize();

    for( int y=0; y< s.height; y++ ) 
    {
        layer->setTileGID(_gid2, Vec2((float)3, (float)y));
    }
    
    _gid2 = (_gid2 + 1) % 80;
}
Exemplo n.º 13
0
TMXMapModel::TMXMapModel(std::string fname)
{
	auto tmx = cocos2d::TMXTiledMap::create(fname);
	this->tmxView = tmx;
	auto ground = tmx->getLayer("Layer0");
	auto dim = ground->getLayerSize();
	this->init(dim.width, dim.height);

	for (int x = 0; x < dim.width; x++)
	{
		for (int y = 0; y < dim.height; y++)
		{
			if (ground->getTileGIDAt(cocos2d::Vec2(x, y)) != 11)
			{
				this->cells[y][x] = CellType::LAND;
			}
		}
	}
}
Exemplo n.º 14
0
 NMap()
 {
     mTileSize = getTileSize();
     mLayerSize = getLayerSize();
 }
Exemplo n.º 15
0
bool TiledMapLayer::init()
{
    if (Layer::init()) {
        
        auto map = TMXTiledMap::create("tiledmap/TestMap.tmx");
        map->setAnchorPoint(Vec2(0.0f, 0.0f));
        map->setPosition(0, 0);
        this->addChild(map);
        
        
        auto mapLayer = map->getLayer("layer1");
        
        Size maxSize = mapLayer->getLayerSize();
        CCLOG("maplayer maxwidth %f maxheight %f" , maxSize.width,maxSize.height);
        
        mapGraph = new GridMap((int)maxSize.width,(int)maxSize.height);
        
        for (int row = 0; row < maxSize.width; row++) {
            for (int col = 0; col < maxSize.height; col++) {
                int gid = mapLayer->getTileGIDAt(Vec2(row,col));
                printf(" %d",gid);
                
                if (gid == 10) {
                    mapGraph->setGridVertexType(row, col, vertex_vertex);
                }
            }
            printf("\n");
        }
        
        Dijkstra dij;
        dij.Execute(*mapGraph, 10, 39 * ID_PARA + 13);
        Vertex * vertex = mapGraph->getVertex(39, 13);
        

//        AStar dij;
//        dij.Execute(*mapGraph, 10, 39 * ID_PARA + 13);
//        Vertex * vertex = mapGraph->getVertex(39, 13);
        
        printf("path tree length %lld \n", dij.pathTree.size());
        
        
//        for (auto it = dij.pathTree.find(vertex) , end = dij.pathTree.end(); it->second != 0&& it != end ; it= dij.pathTree.find(it->second)) {
//            mapLayer->setTileGID(31, Vec2(vertex->getX(), vertex->getY()));
//            vertex = it->second;
//        }
        
        auto end = dij.pathTree.end();
        while (vertex != nullptr) {
            mapLayer->setTileGID(31, Vec2(vertex->getX(), vertex->getY()));
            auto it = dij.pathTree.find(vertex);
            if (it != end && it->second != nullptr) {
                vertex = it->second;
            }else{
                vertex = nullptr;
            }
        }
        
        auto dispatcher = Director::getInstance()->getEventDispatcher();
        auto listener = EventListenerTouchOneByOne::create();
        
        listener->onTouchBegan = CC_CALLBACK_2(TiledMapLayer::onTouchBegan, this);
        listener->onTouchMoved = CC_CALLBACK_2(TiledMapLayer::onTouchMoved, this);
        listener->onTouchEnded = CC_CALLBACK_2(TiledMapLayer::onTouchEnded, this);
        dispatcher->addEventListenerWithSceneGraphPriority(listener, this);
        
        return true;
    }
    
    return false;
}
Exemplo n.º 16
0
void FloorMapLayer::onTouchEnded(Touch *touch, Event *e)
{
    // bugfix: 如果对话框已弹出,就不再执行以下代码,这种情况是在对话框弹出前,touchbegan就已经触发的情况下发生
    // 重现方法: 控制勇士经过怪物,然后鼠标按下等待勇士到达怪物处,弹出提示对话框后,松开鼠标继续弹出
    if (ModalDialogManager::GetInstance()->isShown())
    {
        return;
    }

    // 正在战斗中或自定义忙碌(如开门等待)中则不允许重新走动,以免计算混乱
    if (_warrior->is_fighting() || _warrior->is_lock())
    {
        return;
    }

    // 获取起始点
    auto end_vec2 = _tiled_map->convertTouchToNodeSpace(touch) / 75.0f;
    auto end_pt = Floor::position_t(end_vec2.x, end_vec2.y);
    if (!_paths.empty() && _paths.back() == end_pt)
    {
        return;
    }
    
    auto start_vec2 = _tiled_map->convertToNodeSpace(_warrior->getPosition()) / 75.0f;
    auto start_pt = Floor::position_t(start_vec2.x, start_vec2.y);
    if (start_pt == end_pt)
    {
        return;
    }

    // 获取阻碍点
    auto wall_layer = _tiled_map->getLayer("wall");
    auto wall_layer_size = wall_layer->getLayerSize();
    auto pos = touch->getLocation();
    auto tiles = wall_layer->getTiles();
    std::vector<AStar::node_t> blocks;
    for (uint32_t i = 0; i < (uint32_t)(wall_layer_size.height); ++i)
    {
        for (uint32_t j = 0; j < (uint32_t)(wall_layer_size.width); ++j)
        {
            if (tiles[i * (uint32_t)(wall_layer_size.width) + j] != 0)
            {
                blocks.push_back(AStar::node_t(j, (uint32_t)(wall_layer_size.height) - 1 - i));
            }
        }
    }

    if (std::find(blocks.begin(), blocks.end(), AStar::node_t(end_pt.x, end_pt.y)) != blocks.end() || end_pt.x >= 10 || end_pt.y >= 12)
    {
        return;
    }

    // A星路径
    AStar astar(10, 12);
    astar.set_start_and_end(AStar::node_t(start_pt.x, start_pt.y), AStar::node_t(end_pt.x, end_pt.y));
    astar.set_blocks(blocks);
    std::vector<AStar::node_t> paths = astar.get_path();
    auto stair_iter = std::find_if(paths.begin(), paths.end(), [&](AStar::node_t node) {
        // 找到除了首节点的第一个楼梯节点
        Floor::position_t pos(node.x, node.y);
        return pos != start_pt && (pos == _stair_up.pos || pos == _stair_down.pos);
    });

    if (stair_iter != paths.end())
        paths.erase(++stair_iter, paths.end());

    _paths.clear();
    for (const auto& node : paths)
    {
        _paths.push_back(Floor::position_t(node.x, node.y));
    }

    // 箭头
    _arrow_node->setVisible(true);
    _arrow_node->setPosition(Vec2((end_pt.x + 0.5f) * 75.0f - 50.0f, (end_pt.y + 0.5f) * 75.0f - 50.0f));

    // 路线
    uint32_t index = 0;
    _road_node->removeAllChildren();
    for (auto node : _paths)
    {
        if (index == _paths.size() - 1)
            break;
        auto pos = Vec2((node.x + 0.5f) * 75.0f - 50.0f, (node.y + 0.5f) * 75.0f - 50.0f);
        auto res = "Images/diban" + String::createWithFormat("%d", index % 22)->_string + ".png";
        auto sprite = Sprite::create(res);
        sprite->setPosition(pos);
        _road_node->addChild(sprite);
        ++index;
    }

    // 勇士
    _warrior->stopAllActions();
    step();
}
Exemplo n.º 17
0
bool FloorMapLayer::init(int floor, bool up)
{
    _floor = floor;
    // 由于直接继承自node,需要做一些处理,现在layer的功能全被废弃了,无意义
    setContentSize(Director::getInstance()->getWinSize());

    auto listener = EventListenerTouchOneByOne::create();
    listener->setSwallowTouches(true);
    listener->onTouchBegan = CC_CALLBACK_2(FloorMapLayer::onTouchBegan, this);
    listener->onTouchEnded = CC_CALLBACK_2(FloorMapLayer::onTouchEnded, this);
    _eventDispatcher->addEventListenerWithSceneGraphPriority(listener, this);

    // 加载地图编辑器文件
    auto res = "TileMaps/floor00" + String::createWithFormat("%d", floor)->_string + ".tmx";
    _tiled_map = cocos2d::experimental::TMXTiledMap::create(res);
    if (nullptr != _tiled_map)
    {
        _tiled_map->setPosition(Vec2(-50.0f, -50.0f));
        this->addChild(_tiled_map);
    }

    auto npc_layer = _tiled_map->getLayer("npc");
    auto npc_layer_size = npc_layer->getLayerSize();
    auto npc_tiles = npc_layer->getTiles();
    std::vector<Floor::npc_t> npcs;
    for (uint32_t i = 0; i < (uint32_t)(npc_layer_size.height); ++i)
    {
        for (uint32_t j = 0; j < (uint32_t)(npc_layer_size.width); ++j)
        {
            int32_t gid = (int32_t)(npc_tiles[i * (uint32_t)(npc_layer_size.width) + j]);
            if (gid != 0)
            {
                const Floor::floor_t& floor = Floor::GetInstance()->get_floor_info(_floor);
                Floor::npc_t npc(j, npc_layer_size.height - 1 - i, gid);
                if (floor.is_valid())
                {
                    auto iter = std::find(floor.npcs.begin(), floor.npcs.end(), npc);
                    if (iter == floor.npcs.end())
                    {
                        npc_layer->setTileGID(999, Vec2(j, i));
                    }
                }
                npcs.push_back(npc);
                if (get_tile_prop(gid, "style").asInt() == 6)
                {
                    if (get_tile_prop(gid, "type").asInt() == 2)
                        _stair_up = npcs.back();
                    else
                        _stair_down = npcs.back();
                }
            }
        }
    }

    Floor::GetInstance()->auto_init_floor(_floor, npcs);

    // 路径节点
    _road_node = Node::create();
    if (nullptr != _road_node)
    {
        _road_node->setPosition(Vec2::ZERO);
        this->addChild(_road_node);
    }

    // 勇士骨骼动画节点
    _warrior = WarriorNode::create();
    /*cocostudio::CCBone* bone = _warrior->getBone("sheild1");
    int index = bone->getDisplayManager()->getCurrentDisplayIndex();
    bone->removeDisplay(1);
    bone->changeDisplayByIndex(-1, true);
    cocostudio::CCBone* bone2 = _warrior->getBone("sheild2");
    index = bone2->getDisplayManager()->getCurrentDisplayIndex();
    bone2->removeDisplay(1);
    bone2->changeDisplayByIndex(-1, true);*/
    Floor::position_t pos = up ? _stair_down.pos : _stair_up.pos;
    _warrior->setPosition(Vec2((pos.x + 0.5f) * 75.0f - 50.0f, (pos.y + 0.5f) * 75.0f - 50.0f));
    this->addChild(_warrior);

    // 上方背景
    auto inside_bg = Sprite::create("Images/bg_top2.png");
    auto outside_bg = Sprite::create("Images/bg_top_1.png");
    if (nullptr != outside_bg && nullptr != inside_bg)
    {
        auto win_size = Director::getInstance()->getWinSize();
        outside_bg->setScale(inside_bg->getContentSize().width / outside_bg->getContentSize().width);
        outside_bg->setPosition(Vec2(win_size.width / 2, 1092.0f));
        this->addChild(outside_bg);

        inside_bg->setPosition(Vec2(win_size.width / 2, 1076.0f));
        this->addChild(inside_bg);
    }

    // 点击箭头节点
    _arrow_node = ArrowNode::create();
    if (nullptr != _arrow_node)
    {
        _arrow_node->setPosition(Vec2::ZERO);
        _arrow_node->setVisible(false);
        this->addChild(_arrow_node);
    }

    // 勇士属性面板
    _info_panel = WarriorInfoPanel::create();
    if (nullptr != _info_panel)
    {
        _info_panel->setPosition(Vec2(-10.0f, 825.0f));
        this->addChild(_info_panel);
    }
    
    return true;
}
Exemplo n.º 18
0
void FloorMapLayer::onTouchEnded(Touch *touch, Event *e)
{
    // bugfix: 如果对话框已弹出,就不再执行以下代码,这种情况是在对话框弹出前,touchbegan就已经触发的情况下发生
    // 重现方法: 控制勇士经过怪物,然后鼠标按下等待勇士到达怪物处,弹出提示对话框后,松开鼠标继续弹出
    if (ModalDialogManager::GetInstance()->isShown())
    {
        return;
    }

    // 正在战斗中则不允许重新走动,以免计算混乱
    if (_warrior->is_fighting())
    {
        return;
    }

    // 获取起始点
    auto end_vec2 = _tiled_map->convertTouchToNodeSpace(touch) / 75.0f;
    auto end_pt = node_t(end_vec2.x, end_vec2.y);
    if (!_paths.empty() && _paths.back() == end_pt)
    {
        return;
    }
    
    auto start_vec2 = _tiled_map->convertToNodeSpace(_warrior->getPosition()) / 75.0f;
    auto start_pt = node_t(start_vec2.x, start_vec2.y);
    if (start_pt == end_pt)
    {
        return;
    }


    // 获取阻碍点
    auto wall_layer = _tiled_map->getLayer("wall");
    auto wall_layer_size = wall_layer->getLayerSize();
    auto pos = touch->getLocation();
    auto tiles = wall_layer->getTiles();
    std::vector<node_t> blocks;
    for (uint32_t i = 0; i < (uint32_t)(wall_layer_size.height); ++i)
    {
        for (uint32_t j = 0; j < (uint32_t)(wall_layer_size.width); ++j)
        {
            if (tiles[i * (uint32_t)(wall_layer_size.width) + j] != 0)
            {
                blocks.push_back(node_t(j, (uint32_t)(wall_layer_size.height) - 1 - i));
            }
        }
    }

    if (std::find(blocks.begin(), blocks.end(), end_pt) != blocks.end() || end_pt.x >= 10 || end_pt.y >= 12)
    {
        return;
    }
    
    // npc列表
    npc_t stair_up, stair_down;
    auto npc_layer = _tiled_map->getLayer("npc");
    auto npc_layer_size = npc_layer->getLayerSize();
    auto npc_tiles = npc_layer->getTiles();
    _npcs.clear();
    for (uint32_t i = 0; i < (uint32_t)(npc_layer_size.height); ++i)
    {
        for (uint32_t j = 0; j < (uint32_t)(npc_layer_size.width); ++j)
        {
            int32_t gid = (int32_t)(npc_tiles[i * (uint32_t)(npc_layer_size.width) + j]);
            if (gid != 0)
            {
                _npcs.push_back(npc_t(j, npc_layer_size.height - 1 - i, gid));
                if (get_tile_prop(gid, "style").asInt() == 6)
                {
                    if (get_tile_prop(gid, "type").asInt() == 1)
                        stair_up = _npcs.back();
                    else
                        stair_down = _npcs.back();
                }
            }
        }
    }

    // A星路径
    AStar astar(10, 12);
    astar.set_start_and_end(start_pt, end_pt);
    astar.set_blocks(blocks);
    _paths = astar.get_path();
    auto iter = std::find_if(_paths.begin(), _paths.end(), [&](node_t node) {
        // 找到除了首节点的第一个楼梯节点
        return (node.x != start_pt.x || node.y != start_pt.y) &&
            (node.x == stair_up.x && node.y == stair_up.y || node.x == stair_down.x && node.y == stair_down.y);
    });

    if (iter != _paths.end())
        _paths.erase(++iter, _paths.end());

    // 箭头
    _arrow_node->setVisible(true);
    _arrow_node->setPosition(Vec2((end_pt.x + 0.5f) * 75.0f - 50.0f, (end_pt.y + 0.5f) * 75.0f - 50.0f));

    // 路线
    uint32_t index = 0;
    _road_node->removeAllChildren();
    for (auto node : _paths)
    {
        if (index == _paths.size() - 1)
            break;
        auto pos = Vec2((node.x + 0.5f) * 75.0f - 50.0f, (node.y + 0.5f) * 75.0f - 50.0f);
        auto res = "Images/diban" + String::createWithFormat("%d", index % 22)->_string + ".png";
        auto sprite = Sprite::create(res);
        sprite->setPosition(pos);
        _road_node->addChild(sprite);
        ++index;
    }

    // 勇士
    _warrior->stopAllActions();
    step();
}