Skip to content

Commit

Permalink
Merge pull request #63 from Geodan/add_multiple_source_epsg_codes_sup…
Browse files Browse the repository at this point in the history
…port

add multiple source epsg code support
  • Loading branch information
bertt authored Jun 13, 2024
2 parents 0e8bd98 + 7c65524 commit d32a6c2
Show file tree
Hide file tree
Showing 5 changed files with 50 additions and 15 deletions.
18 changes: 18 additions & 0 deletions src/DatabaseReader.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
using System.Data;

namespace i3dm.export;
public static class DatabaseReader
{
public static int ReadScalar(IDbConnection conn, string sql)
{
conn.Open();
var command = conn.CreateCommand();
command.CommandText = sql;
var reader = command.ExecuteReader();
reader.Read();
var scalar = reader.GetInt32(0);
reader.Close();
conn.Close();
return scalar;
}
}
12 changes: 6 additions & 6 deletions src/ImplicitTiling.cs
Original file line number Diff line number Diff line change
Expand Up @@ -29,11 +29,11 @@ public static byte[] GetSubtreeBytes(string tileAvailability, string contentAvai
return subtreebytes;
}

public static List<Tile> GenerateTiles(Options o, NpgsqlConnection conn, BoundingBox bbox, Tile tile, List<Tile> tiles, string contentDirectory, int epsg, bool useGpuInstancing = false)
public static List<Tile> GenerateTiles(Options o, NpgsqlConnection conn, BoundingBox bbox, Tile tile, List<Tile> tiles, string contentDirectory, int source_epsg, bool useGpuInstancing = false)
{
var where = (o.Query != string.Empty ? $" and {o.Query}" : String.Empty);

var numberOfFeatures = InstancesRepository.CountFeaturesInBox(conn, o.Table, o.GeometryColumn, bbox, where);
var numberOfFeatures = InstancesRepository.CountFeaturesInBox(conn, o.Table, o.GeometryColumn, bbox, where, source_epsg);

if (numberOfFeatures == 0)
{
Expand Down Expand Up @@ -62,13 +62,13 @@ public static List<Tile> GenerateTiles(Options o, NpgsqlConnection conn, Boundin
var bboxQuad = new BoundingBox(xstart, ystart, xend, yend);

var new_tile = new Tile(tile.Z + 1, tile.X * 2 + x, tile.Y * 2 + y);
GenerateTiles(o, conn, bboxQuad, new_tile, tiles, contentDirectory, epsg, useGpuInstancing);
GenerateTiles(o, conn, bboxQuad, new_tile, tiles, contentDirectory, source_epsg, useGpuInstancing);
}
}
}
else
{
var bytes = CreateTile(o, conn, bbox, epsg, where, useGpuInstancing);
var bytes = CreateTile(o, conn, bbox, source_epsg, where, useGpuInstancing);
var extension = useGpuInstancing? "glb": "cmpt";
var file = $"{contentDirectory}{Path.AltDirectorySeparatorChar}{tile.Z}_{tile.X}_{tile.Y}.{extension}";
Console.Write($"\rCreating tile: {file} ");
Expand All @@ -83,9 +83,9 @@ public static List<Tile> GenerateTiles(Options o, NpgsqlConnection conn, Boundin
return tiles;
}

private static byte[] CreateTile(Options o, NpgsqlConnection conn, BoundingBox tileBounds, int epsg, string where, bool useGpuInstancing = false)
private static byte[] CreateTile(Options o, NpgsqlConnection conn, BoundingBox tileBounds, int source_epsg, string where, bool useGpuInstancing = false)
{
var instances = InstancesRepository.GetInstances(conn, o.Table, o.GeometryColumn, tileBounds, epsg, where, (bool)o.UseScaleNonUniform, useGpuInstancing);
var instances = InstancesRepository.GetInstances(conn, o.Table, o.GeometryColumn, tileBounds, source_epsg, where, (bool)o.UseScaleNonUniform, useGpuInstancing);
var tile = TileHandler.GetTile(instances, (bool)o.UseExternalModel, (bool)o.UseScaleNonUniform, useGpuInstancing);
return tile;
}
Expand Down
15 changes: 8 additions & 7 deletions src/InstancesRepository.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,14 +9,14 @@ namespace i3dm.export;

public static class InstancesRepository
{
internal static int CountFeaturesInBox(NpgsqlConnection conn, string geometryTable, string geometryColumn, BoundingBox bbox, string where)
internal static int CountFeaturesInBox(NpgsqlConnection conn, string geometryTable, string geometryColumn, BoundingBox bbox, string where, int source_epsg)
{
var fromX = bbox.XMin.ToString(CultureInfo.InvariantCulture);
var fromY = bbox.YMin.ToString(CultureInfo.InvariantCulture);
var toX = bbox.XMax.ToString(CultureInfo.InvariantCulture);
var toY = bbox.YMax.ToString(CultureInfo.InvariantCulture);

string whereStatement = GetWhere(geometryColumn, where, fromX, fromY, toX, toY);
string whereStatement = GetWhere(geometryColumn, where, fromX, fromY, toX, toY, source_epsg);

var sql = $"select count({geometryColumn}) from {geometryTable} where {whereStatement}";
conn.Open();
Expand All @@ -28,21 +28,22 @@ internal static int CountFeaturesInBox(NpgsqlConnection conn, string geometryTab
return count;
}

private static string GetWhere(string geometryColumn, string where, string fromX, string fromY, string toX, string toY)
private static string GetWhere(string geometryColumn, string where, string fromX, string fromY, string toX, string toY, int source_epsg)
{
return $"ST_Intersects({geometryColumn}, ST_MakeEnvelope({fromX}, {fromY}, {toX}, {toY}, 4326)) {where}";
return $"ST_Intersects({geometryColumn}, ST_Transform(ST_MakeEnvelope({fromX}, {fromY}, {toX}, {toY}, 4326), {source_epsg})) {where}";
}

public static List<Instance> GetInstances(NpgsqlConnection conn, string geometryTable, string geometryColumn, BoundingBox bbox, int epsg, string where = "", bool useScaleNonUniform = false, bool useGpuInstancing = false)
public static List<Instance> GetInstances(NpgsqlConnection conn, string geometryTable, string geometryColumn, BoundingBox bbox, int source_epsg, string where = "", bool useScaleNonUniform = false, bool useGpuInstancing = false)
{
var target_epsg = 4978;
var fromX = ToInvariantCulture(bbox.XMin);
var fromY = ToInvariantCulture(bbox.YMin);
var toX = ToInvariantCulture(bbox.XMax);
var toY = ToInvariantCulture(bbox.YMax);

var scaleNonUniform = useScaleNonUniform ? "scale_non_uniform as scalenonuniform, " : string.Empty;
conn.Open();
var select = $"SELECT ST_ASBinary(ST_Transform(st_force3d({geometryColumn}), {epsg})) as position, scale, {scaleNonUniform} model, tags";
var select = $"SELECT ST_ASBinary(ST_Transform(st_force3d({geometryColumn}), {target_epsg})) as position, scale, {scaleNonUniform} model, tags";

if (useGpuInstancing)
{
Expand All @@ -53,7 +54,7 @@ public static List<Instance> GetInstances(NpgsqlConnection conn, string geometry
select += ", rotation";
}

var sql = FormattableString.Invariant($"{select} FROM {geometryTable} where {GetWhere(geometryColumn, where, fromX, fromY, toX, toY)}");
var sql = FormattableString.Invariant($"{select} FROM {geometryTable} where {GetWhere(geometryColumn, where, fromX, fromY, toX, toY, source_epsg)}");
var res = conn.Query<Instance>(sql).AsList();
conn.Close();
return res;
Expand Down
7 changes: 5 additions & 2 deletions src/Program.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
using ShellProgressBar;
using subtree;
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
Expand Down Expand Up @@ -48,7 +49,6 @@ static void Main(string[] args)
}

var conn = new NpgsqlConnection(o.ConnectionString);
var epsg = 4978;

var heightsArray = o.BoundingVolumeHeights.Split(',');
var heights = new double[2] { double.Parse(heightsArray[0]), double.Parse(heightsArray[1]) };
Expand Down Expand Up @@ -78,6 +78,9 @@ static void Main(string[] args)
Console.WriteLine($"Bounding box for table (WGS84): {Math.Round(bbox_wgs84.XMin, 4)}, {Math.Round(bbox_wgs84.YMin, 4)}, {Math.Round(bbox_wgs84.XMax, 4)}, {Math.Round(bbox_wgs84.YMax, 4)}");
Console.WriteLine($"Vertical for table (meters): {zmin}, {zmax}");

var source_epsg = SpatialReferenceRepository.GetSpatialReference(conn, o.Table, geom_column, o.Query);
Console.WriteLine($"Spatial reference of {o.Table}.{o.GeometryColumn}: {source_epsg}");

var rootBoundingVolumeRegion = bbox_wgs84.ToRadians().ToRegion(zmin, zmax);

var center_wgs84 = bbox_wgs84.GetCenter();
Expand Down Expand Up @@ -115,7 +118,7 @@ static void Main(string[] args)
Console.WriteLine("Start generating tiles...");

var tile = new Tile(0, 0, 0);
var tiles = ImplicitTiling.GenerateTiles(o, conn, bbox_wgs84, tile, new List<Tile>(), contentDirectory, epsg, (bool)o.UseGpuInstancing);
var tiles = ImplicitTiling.GenerateTiles(o, conn, bbox_wgs84, tile, new List<Tile>(), contentDirectory, source_epsg, (bool)o.UseGpuInstancing);

Console.WriteLine();
Console.WriteLine($"Tiles written: {tiles.Count}");
Expand Down
13 changes: 13 additions & 0 deletions src/SpatialReferenceRepository.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
using System.Data;

namespace i3dm.export;
public static class SpatialReferenceRepository
{
public static int GetSpatialReference(IDbConnection conn, string geometry_table, string geometry_column, string query = "")
{
var q = query == "" ? "" : $"WHERE {query}";
var sql = $"SELECT ST_SRID({geometry_column}) from {geometry_table} {q} limit 1";
var sr = DatabaseReader.ReadScalar(conn, sql);
return sr;
}
}

0 comments on commit d32a6c2

Please sign in to comment.