3d tileset clamp to ground

Hi, i want know it’s possible to clamp a 3dtileset(b3dm) to ground when has a terrainProvider(from cesium world terrain)?

@QianWu184

It is indeed possible! As you can see in this guide, b3dm is a supported tiler data format.

Thus, we can use the following guide to set the location of the data and clamp it to the ground, once it is uploaded to Cesium ion.

Let me know if this helps! I am happy to address any lingering questions or concerns :grinning_face_with_smiling_eyes:

Best,
Sam

There’s an extended answer to this as well, which is that there’s no property on a tileset to clamp it to ground, but there are ways to transform the viewed tiles into the right place. It’s not straight-forward, of course, but similarily to the guides above you can do it through the Cesium API / code.

So, in short; If you can do it on the processing side (as you create the tileset), that’s the best answer. In code it gets complicated, but it is still doable (look for tileset transforms). It often comes down to how accurate your tileset is (position, rotation, scale, uniformity, etc.), but if it’s reasonably accurate you can do something like this;

Load your tileset, but don’t show it, and find the bounding middle point of your tileset (should be in the root tile), then sample terrain at that point, then show your model on the map and then sample your model at the same point you sampled the terrain. The rest is basically a transform height to the same as the terrain sample. That’s the short version, but give it a stab first. There are some issues with sampling terrains and models unless the camera is looking in the right spot, so make sure the camera is looking at that sampling point from a reasonable distance (but this comes back to your application and design). And if you’re dealing with pointclouds, sampling becomes even more complicated.

If your model isn’t accurate, you’ll see it quickly and all sorts of pain and suffering will follow (unless you’re a math wiz, in which case it should be reasonably easy to follow the traonsformation matrix model). It then becomes an issue of making the model rotate and scale correctly, and then save those parameters somewhere, and apply them every time you add in this model.

Let us know what you’re trying to do.

Cheers,

Alex

2 Likes

@Alexander_Johannesen

Thank you very much for adding more details :smiley:

Best,
Sam

1 Like

Thank you very much.I’ll try this in my project

Hi, I have a 3D tileset, and I want to clamp it to the terrain ground.
I tried to make a recursive function to put every single tile above the ground, at the corrected height, calculated by the position (lat and long) of each tile, but it did not work since the function does not work with the root of the tileset.

Does anyone have some idea? or is there any function in Cesium that does it automatically?
thanks

Hi @luigiumana,

You should be able to adjust the tileset modelMatrix property rather than apply the height to each tile individually.

Hi @Gabby_Getz ,
thanks, but my problem is different: I have the exact height of the tiles and the exact coordinates, and I want to clamp them into terrain ground, which has different ground height for each couple of coordinates. That the reason why I opted to calculate one by one

Got it, thanks.

Usually for cases like this, the building are clamped to a terrain provider before tiling with 3D Tiles, as Alex describes above.

For example, this is how the Cesium ion building tiler works.

If you can let us know the problem you’re running into with the root, we can help troubleshoot.

[quote=“Gabby_Getz, post:9, topic:14685”]

here you can find my code:
https://sandcastle.cesium.com/#c=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

as you can see, the function set_fixed_height(tile, h) works properly, as in the link you sent me a few days ago
in fact, if you run line 75, every tile is h taller.
So I decided to utilize this function passing only a specific tile, with a specific height, calculated by the terrain level;
you can find it in the function processTile(tile)

Thank you very much for your help

Hi Alexander, do you have an example of this solution you are suggesting?
Thank you