Separate sync and async parts of QuadtreeRasterOverlayTileProvider::mapRasterTilesToGeometryTile
As originally identified in https://github.com/CesiumGS/cesium-native/issues/303#issuecomment-893553334, mapRasterTilesToGeometryTile does a bunch of synchronous work to figure out which raster overlay quadtree tiles overlap a given geometry tile. And then it also calls getQuadtreeTile for each of those quadtree tiles to get a shared future for its image data.
This would be much cleaner if we separate this into two functions. The first is fully synchronous and returns a list of mapped tile IDs. And the second takes a list of tile IDs and returns either vector<SharedFuture<LoadedQuadtreeImage>> or Future<Vector<LoadedQuadtreeImage>>`.
In addition to being conceptually nicer, it would also allow us to write tests for the tricky synchronous part without needing to deal with the asynchronous part.
Really the only downside to this we need an extra temporary vector and need to make two passes over it (once to populate it, once to read it), but the cost should be plenty low here. Functional programming languages have great ways to achieve this composability without the temporary and two passes. I think C++20's ranges and coroutines would be similar, but I'm not sure of their cost.