retroplasma / earth-reverse-engineering

Reversing Google's 3D satellite mode
2.24k stars 213 forks source link

[Research] Normalize mesh with a reference point as origin #30

Open LexSong opened 5 years ago

LexSong commented 5 years ago

In my testing fork, I add two scripts to handle mesh normalization.

In normalize_obj.py, the script normalize the mesh with a reference XYZ point instead of the mesh center. Therefore we could normalize several meshes with the same origin and keep their relative position. The script also rotate the mesh with latitude and longitude of the reference point, to align north/south and east/west axes.

To find the reference point, in another script find_obj_mid_point.py, I compute the mesh midpoint by convert mesh vertices to latitude/longitude/altitude and calculate the midpoint's location. The trick here is that we don't have to calculate the midpoint of high resolution mesh. We should use a low resolution mesh instead to avoid unnecessary computation.

Rakiah commented 5 years ago

@LexSong you're using @ character in normalize_obj.py file R = Ry @ Rz like so, it doesn't seem supported by lot of python installations, can you explain what does it do ?

LexSong commented 5 years ago

That's matrix multiplication operator. It basically apply rotation matrix on vertices to align horizon to the Y/Z plane.

Rakiah commented 5 years ago

Ah thank you, this require python3.5 it seems (Debian has 3.4 only by default that's why)

LexSong commented 5 years ago

You could use numpy.dot(a, b) to replace a @ b.

bicubic commented 5 years ago

What units does the vertex position currently represent?

I want to translate them to latlong space, and I want to remove the rotation. I basically want to transform the mesh into webmercator space. Happy to do the work, just need some info to start with.

Rakiah commented 5 years ago

the vertices are actually postionned correctly in a 3D perfect sphere based on lat/lon, you can remove entirely the matrices operations in the initial dump_obj script to get the vertices based on a 0,0 reference point for each tile without rotation if that's what you want

LexSong commented 5 years ago

It's difficult to convert to Mercator projection correctly.

First, Mercator projection have different scale based on latitudes. Therefore you must also scale the height based on each vertex's location. Second, the heights in Google Earth is not correct. It doesn't match the ellipsoid or the sea level. We could calculate each vertex's distance to the earth center, but we're not sure how to scale the distance to make the shape correct.

chris-aeviator commented 3 years ago

@LexSong could you please describe step by step how to work with the scripts? My goal here is to have a bounding box high res stitched mesh, e.g. for the use in Blender.

To download a large area I understood 1) get the octants of the desired zoom level with python find_overlaps.py 49.952565726628116 7.038781866798934 50.00740786097225 7.191606713983672 2) get the long list of octants of the desired bounding box to be downloaded with node dump_obj.js 30604072704072 30604072704070 30604072704073 30604072704071 30604072704053 30604072704052 30604072704043 30604072704063 30604072704061 30604072704062 30604072704060 30604072704042 14 3) ... 4)...

On a single octant dump I would now run center_scale_obj.js downloaded_data/obj/.../octant.obj , from my understanding your scripts should help here. Could you please explain what those single functionalities mean and how to use them to get a bounding box high res mesh.

UPDATE:

nevermind - I have not used your tool since 2019 and I'm happy to see the files are nowadays dumped into a single OBJ and correctly stitched - AWESOME!

HakkaTjakka commented 3 years ago

I've adapted this repo for that. https://github.com/HakkaTjakka/MinecraftWorldEditor/tree/master/EARTH It subtracts some mid point from all objects leaving more decimals behind the floating point when using floats (32 bit) instead of double. The less before the decimal point the more behind it. In the program it adds the values for transformations again if needed. Get your floats as small as possible leaves most precision behind the decimal point. The Minecraftworldeditor shows more calculations and examples how to handle the 3d data. Like opengl renderer, recording, spline interpolation, superlarge poster, voxelizer, conversion into Minecraft, shaders on the data. Msg for help.