using ExportMap.db; using ExportMap.Models; using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Web; namespace ExportMap.cs { public class PyLasUtils { /// /// 获取路径 /// public static string GetPath(int id) { return Path.Combine(SGUtils.LFData, "3d\\3dtiles\\las", id.ToString()); } /// /// 获取发布地址 /// public static string GetReleaseUrl(string path) { return "{host}/LFData/" + path.Replace("\\", "/"); } /// /// 生成 /// /// XYZ参数 /// 错误信息 /// 数据发布ID集合 public static List Generate(XYZArgs args, ref string err) { try { List list = XYZUtils.SelectMetas(args.ids, "and type in ('las', 'laz')"); if (null == list || list.Count == 0) return null; string pyPath = Tools.GetSetting("pythonFolder"); string uploadFolder = Tools.GetSetting("uploadFolder"); List ids = new List(); foreach (SysMeta meta in list) { string lasPath = Path.Combine(uploadFolder, meta.path); if (!File.Exists(lasPath)) continue; string outPath = GetPath(meta.id); if (Directory.Exists(outPath)) Tools.DelPath(outPath); if (!Directory.Exists(outPath)) Directory.CreateDirectory(outPath); //int idx = args.ids.IndexOf(meta.id); // args.srids[idx], args.zs[idx]) List cmds = new List(); cmds.Add(string.Format("set PYTHONHOME={0}", pyPath)); cmds.Add(string.Format("{0}\\Scripts\\py3dtiles.exe convert --overwrite {1} --out {2}", pyPath, lasPath, outPath)); SysTask task = TaskDBHelper.CreateTask(args, meta, "LAS", "点云数据(LAS)"); err = Tools.ExecCmd(task, cmds, false); err = null; string jsonFile = Path.Combine(outPath, "tileset.json"); if (File.Exists(jsonFile)) { string path = jsonFile.Replace(Tools.GetSetting("lfData") + "\\", ""); int pubid = InsertToDB(meta, args, path); if (pubid > 0) ids.Add(pubid); } } return ids; } catch (Exception ex) { LogOut.Error(ex.Message + "\r\n" + ex.StackTrace); err = ex.Message; return null; } } /// /// 插入数据库 /// private static int InsertToDB(SysMeta meta, XYZArgs args, string path) { //if (PubDBHelper.IsPublish(meta.id)) return 1; int pubid = PubDBHelper.GetPushlishId(meta.id); if (pubid > 0) { PubDBHelper.UpdatePublish(pubid, meta.name, args.userId, null); return pubid; } SysPublish sys = Tools.NewPublish(meta, args, GetReleaseUrl(path), path); sys.json = GetLasGeomJSON(Path.Combine(Tools.GetSetting("uploadFolder"), meta.path), meta.id); pubid = PubDBHelper.InsertPublish(sys); if (pubid > 0) { sys.id = pubid; PubDBHelper.InsertLayer(sys, meta); PubDBHelper.InsertMetaPub(meta.id, pubid, args.userId); } return pubid; } /// /// 坐标转换 * /// public static void CsTransform(string epsg, double x, double y, double z = 0) { List cmds = new List(); string gdalPath = Tools.GetSetting("gdalPath"); cmds.Add(string.Format("\"{0}\\gdaltransform.exe\" -s_srs EPSG:{1} -t_srs EPSG:4326", gdalPath, epsg.Replace("EPSG:", ""))); cmds.Add(string.Format("echo {0} {1} {2}", x, y, z)); string rs = null; string str = Tools.ExecCmd(cmds, ref rs); //return rs; } /// /// 获取las坐标JSON /// public static string GetLasGeomJSON(string lasFile, int id) { try { string cmd = string.Format("\"{0}\\lasinfo.exe\" \"{1}\"", Tools.GetSetting("tilerPath"), lasFile); string rs = Tools.ExecCmd(new List { cmd }); if (string.IsNullOrEmpty(rs)) return null; string[] strs = rs.Split(new string[] { "\r\n" }, StringSplitOptions.RemoveEmptyEntries); string epsg = GetEpsgFromStrs(strs); string minStr = GetCoordFromStrs(strs, "min x y z:"); string maxStr = GetCoordFromStrs(strs, "max x y z:"); string scaleStr = GetCoordFromStrs(strs, "scale factor x y z:"); if (string.IsNullOrEmpty(epsg) || string.IsNullOrEmpty(minStr) || string.IsNullOrEmpty(maxStr) || string.IsNullOrEmpty(scaleStr)) return null; string[] minXYZ = minStr.Split(new string[] { " " }, StringSplitOptions.RemoveEmptyEntries); string[] maxXYZ = maxStr.Split(new string[] { " " }, StringSplitOptions.RemoveEmptyEntries); string[] scales = scaleStr.Split(new string[] { " " }, StringSplitOptions.RemoveEmptyEntries); double minX = double.Parse(minXYZ[0]), minY = double.Parse(minXYZ[1]), minZ = double.Parse(minXYZ[2]); double maxX = double.Parse(maxXYZ[0]), maxY = double.Parse(maxXYZ[1]), maxZ = double.Parse(maxXYZ[2]); double x = (minX + maxX) / 2, y = (minY + maxY) / 2, z = maxZ, scale = Math.Round(1 / double.Parse(scales[0]), 2) / 10; string url = ExportUtil.LFServer + "/publish/selectCsTransform?token=" + Tools.Token + "&x=" + x + "&y=" + y + "&epsg=" + epsg; rs = ExportUtil.GetData(url); if (string.IsNullOrEmpty(rs)) return null; strs = rs.Replace("\"", "").Split(new string[] { "," }, StringSplitOptions.None); x = double.Parse(strs[0]); y = double.Parse(strs[1]); return string.Format("{{\"lon\":{0},\"lat\":{1},\"height\":{2},\"yaw\":0,\"alpha\":1,\"modelid\":\"DbId\",\"scale\":{3},\"lasId\":{4}}}", x, y, z, scale, id); } catch (Exception ex) { LogOut.Error(ex.StackTrace); return null; } } /// /// 从字符串数组中获取EPSG /// private static string GetEpsgFromStrs(string[] strs) { foreach (string str in strs) { if (str.Contains("key 3072 ")) { int start = str.IndexOf("value_offset") + 12; int end = str.IndexOf("-", start); return str.Substring(start, end - start).Replace(" ", ""); } } return null; } /// /// 从字符串数组中获取坐标 /// private static string GetCoordFromStrs(string[] strs, string key) { foreach (string str in strs) { if (str.Contains(key)) { return str.Replace(key, ""); } } return null; } } }