Select to view content in your preferred language

Trying to load more than one tpk file when I am offline

1179
2
Jump to solution
03-13-2017 04:10 AM
TorbenWiggerich
New Contributor III

Hi all ,

I am trying to load two tpk - files. When I am ONLINE I have absolutly no problems everthing works fine .

But when I am, from the beginning of the start of my application, OFFLINE I can't see anything.

So I started by replacing the following line:

mp_basemap = Esri::ArcGISRuntime::Basemap::imagery( this );

With the following line:

mp_basemap = new Esri::ArcGISRuntime::Basemap( this );

Now I can see the first OFFLINE tpk file. But the region is somewho selected to exactly this image. I cannot zoom further out or go to another place. Everthing is just inside this region...

How I can I remove this region?

This is my code:

mp_basemap = new Esri::ArcGISRuntime::Basemap( this );
TileCache * tileCache = new TileCache( "<path>\\Test.tpk", this);
ArcGISTiledLayer* tiledLayer = new ArcGISTiledLayer( tileCache, this );
mp_basemap->baseLayers()->append( tiledLayer );

TileCache * tileCache2 = new TileCache( "<path>\\Test2.tpk", this);
ArcGISTiledLayer* tiledLayer2 = new ArcGISTiledLayer( tileCache2, this );
mp_basemap->baseLayers()->append( tiledLayer2 );

So the second tpk file is not shown. This is the case when the second tpk file is far away from the first.

If the second tpk file is close too the first tpk file, it will be shown, but the selected region is just from the first loaded layer. It does not seem to extent it.

With kind regards

Torben

0 Kudos
1 Solution

Accepted Solutions
LukeSmallwood
Esri Contributor

Hi Torben,

I am able to reproduce the behaviour you are describing - I will investigate this a bit further to see what we would expect to happen in this situation. In the meantime, you can try this workaround: essentially, you need to load the 2  ArcGISTiledLayers before using them for the basemap/map.

You also need to ensure that your tpks are in the same Spatial Reference.

Here is some example code that fixes the problem for me - basically, we call load on the 2 layers and when both are loaded we call the setMap function. I've added a GraphicsOverlay to the map so you can see where the 2 tpks are located.

    TileCache * tileCache2 = new TileCache( "<path>//tpk1.tpk", this);
    m_lyr2 = new ArcGISTiledLayer( tileCache2, this );
    m_lyr2->load();
    TileCache * tileCache = new TileCache( "<path>//tpk2.tpk", this);
    m_lyr1 = new ArcGISTiledLayer( tileCache, this );
    m_lyr1->load();
    connect(m_lyr1, &ArcGISTiledLayer::doneLoading, this, [this](Error error)
    {
        if (m_lyr1->loadStatus() != LoadStatus::Loaded)
            return;
        qDebug() << "m_lyr1 loaded";
        qDebug() << m_lyr1->spatialReference().wkid();
        if (m_lyr2->loadStatus() == LoadStatus::Loaded)
            setMap();
    });
   connect(m_lyr2, &ArcGISTiledLayer::doneLoading, this, [this](Error error)
    {
        if (m_lyr2->loadStatus() != LoadStatus::Loaded)
            return;
        qDebug() << "m_lyr2 loaded";
        qDebug() << m_lyr2->spatialReference().wkid();
        if (m_lyr1->loadStatus() == LoadStatus::Loaded)
            setMap();
    });

...

void ExampleCode::setMap()
{
    if (m_map)
        return;
    Basemap* bm = new Esri::ArcGISRuntime::Basemap( this );
    bm->baseLayers()->append(m_lyr2);
    bm->baseLayers()->append(m_lyr1);
    m_map = new Map(m_lyr1->spatialReference(), this);
    m_map->setBasemap(bm);
    m_mapView->setMap(m_map);
    GraphicsOverlay* gO = new GraphicsOverlay(this);
    SimpleMarkerSymbol* sym = new SimpleMarkerSymbol(SimpleMarkerSymbolStyle::Circle, Qt::red, 5, this);
    Graphic* g1 = new Graphic(m_lyr1->fullExtent().center(), sym, this);
    Graphic* g2 = new Graphic(m_lyr2->fullExtent().center(), sym, this);
    gO->graphics()->append(g1);
    gO->graphics()->append(g2);
    m_mapView->graphicsOverlays()->append(gO);
}

I hoe that's helpful,

Luke

View solution in original post

2 Replies
LukeSmallwood
Esri Contributor

Hi Torben,

I am able to reproduce the behaviour you are describing - I will investigate this a bit further to see what we would expect to happen in this situation. In the meantime, you can try this workaround: essentially, you need to load the 2  ArcGISTiledLayers before using them for the basemap/map.

You also need to ensure that your tpks are in the same Spatial Reference.

Here is some example code that fixes the problem for me - basically, we call load on the 2 layers and when both are loaded we call the setMap function. I've added a GraphicsOverlay to the map so you can see where the 2 tpks are located.

    TileCache * tileCache2 = new TileCache( "<path>//tpk1.tpk", this);
    m_lyr2 = new ArcGISTiledLayer( tileCache2, this );
    m_lyr2->load();
    TileCache * tileCache = new TileCache( "<path>//tpk2.tpk", this);
    m_lyr1 = new ArcGISTiledLayer( tileCache, this );
    m_lyr1->load();
    connect(m_lyr1, &ArcGISTiledLayer::doneLoading, this, [this](Error error)
    {
        if (m_lyr1->loadStatus() != LoadStatus::Loaded)
            return;
        qDebug() << "m_lyr1 loaded";
        qDebug() << m_lyr1->spatialReference().wkid();
        if (m_lyr2->loadStatus() == LoadStatus::Loaded)
            setMap();
    });
   connect(m_lyr2, &ArcGISTiledLayer::doneLoading, this, [this](Error error)
    {
        if (m_lyr2->loadStatus() != LoadStatus::Loaded)
            return;
        qDebug() << "m_lyr2 loaded";
        qDebug() << m_lyr2->spatialReference().wkid();
        if (m_lyr1->loadStatus() == LoadStatus::Loaded)
            setMap();
    });

...

void ExampleCode::setMap()
{
    if (m_map)
        return;
    Basemap* bm = new Esri::ArcGISRuntime::Basemap( this );
    bm->baseLayers()->append(m_lyr2);
    bm->baseLayers()->append(m_lyr1);
    m_map = new Map(m_lyr1->spatialReference(), this);
    m_map->setBasemap(bm);
    m_mapView->setMap(m_map);
    GraphicsOverlay* gO = new GraphicsOverlay(this);
    SimpleMarkerSymbol* sym = new SimpleMarkerSymbol(SimpleMarkerSymbolStyle::Circle, Qt::red, 5, this);
    Graphic* g1 = new Graphic(m_lyr1->fullExtent().center(), sym, this);
    Graphic* g2 = new Graphic(m_lyr2->fullExtent().center(), sym, this);
    gO->graphics()->append(g1);
    gO->graphics()->append(g2);
    m_mapView->graphicsOverlays()->append(gO);
}

I hoe that's helpful,

Luke

TorbenWiggerich
New Contributor III

Hi Luke,

thank you very much .

It is helpful, and works as expected .

Torben