上篇是关于osgb-->gltf的内容,如有需要,请自行查阅。
如果想了解gltf文件批量显示的问题,可以直接看本篇内容。
一、文件组织结构
在完成了上一篇中一堆操作之后,我们得到了非常多(看你的项目)的gltf模型以及存储这些模型参数的json文件,我把json文件再贴出来,并说一下是什么意思。
[{"ModelName":"point1",
"LocationX":"37.151825566666666",
"LocationY":"111.15182556666667",
"LocationZ":"5.9165",
"Matrix3":"0.7722797,0.6352827,-2.980228E-08,-2.494678E-08,7.723833E-08,1,0.6352827,-0.7722797,7.549784E-08"},
{...},{...}]
其中ModelName是指这个json对象所指向的模型名称,并且这也是模型的文件名;LocationX指的是纬度,正代表北纬,负代表南纬;LocationY指的是经度,正代表东经,负代表西经;LocationZ指的是高程;Matrix3是一个3阶矩阵,定义了模型的姿态。其实这里Location我应该改成latitude啥的,但是因为懒没改,大家可以自行修改代码把它改过来。
二、批量显示模型
我是以Cesium(1.47)-HelloWorld的demo来进行演示,具体真要使用可以自己弄个服务器写个接口来搞一下。
首先把你的json文件放在gltf模型文件夹中,并且一并复制到Cesium-1.47/Apps/SampleData/models文件夹下。在HelloWorld.html文件中加入以下代码:
1.引入jquery,自己去下,然后和HelloWorld.html放在一个位置就可以了
<script type="text/javascript" src="jquery-3.3.1.js"></script>
2.执行自己写的程序
<script type="text/javascript" src="ReadJSONandShowModel.js"></script>
3.我们具体来看一下ReadJSONandShowModel.js里面都写了些什么
// 读取json文件,并在cesium上显示
var viewer = new Cesium.Viewer('cesiumContainer');
var data;
$.ajax({
url : "../Apps/SampleData/models/ConvertFinished/Building_finished.json",
datatype: "json",
async : true,
data :{},
success : function(result) {
var data = JSON.stringify(result);
var dataArray=JSON.parse(data);
console.log(dataArray);
show(dataArray);
}
});
function show(dataArray){
console.log(dataArray.length);
for (let i = 0; i < dataArray.length; i++) {
let FileName = dataArray[i].ModelName;
let latitude=dataArray[i].LocationX;
let longitude=dataArray[i].LocationY;
let height=dataArray[i].LocationZ;
let Matrix3=dataArray[i].Matrix3;
let M=Matrix3.split(",");
console.log(longitude+","+latitude);
let matrix3=new Cesium.Matrix3(M[0],M[1],M[2],M[3],M[4],M[5],M[6],M[7],M[8]);
let x;
let Matrix4 = Cesium.Matrix4.fromRotationTranslation(
matrix3,Cesium.Cartesian3.fromDegrees(longitude,latitude,height),x);
let entity = viewer.entities.add({
position : Cesium.Cartesian3.fromDegrees(longitude, latitude,height),
model : {
uri : '../Apps/SampleData/models/ConvertFinished/'+FileName+'.gltf',
modelMatrix : Matrix4,
scale : 1
}
});
}
}
要注意在这里用到了三阶矩阵转化为四阶矩阵的方法,具体可以查看API文档。
三、其他
1.接上一篇的问题,FME不行,怎么办?
我换了一种转换工具,使用的是OSG——osgconv工具。首先我们需要安装OSG,具体安装过程请按照自己的电脑信息自行搜索,我参考的文章是这篇,感谢作者,但是请大家注意,安装完成后需要重启计算机才能使用,但是他的代码不能用,不知道神马原因。同样的,我们要解决批量生产的问题,具体请看代码:
#include "stdafx.h"
#include "io.h"
#include <fstream>
#include <iostream>
#include <string>
#include <sstream>
#include <vector>
#include <string>
using namespace std;
void getAllFiles(string path, vector<string>& files)
{
//文件句柄
long hFile = 0;
//文件信息
struct _finddata_t fileinfo; //很少用的文件信息读取结构
string p; //string类很有意思的一个赋值函数:assign(),有很多重载版本
if ((hFile = _findfirst(p.assign(path).append("\\*").c_str(), &fileinfo)) != -1)
{
do
{
if ((fileinfo.attrib & _A_SUBDIR)) //判断是否为文件夹
{
if (strcmp(fileinfo.name, ".") != 0 && strcmp(fileinfo.name, "..") != 0)
{
files.push_back(p.assign(path).append("/").append(fileinfo.name));//保存文件夹名字
getAllFiles(p.assign(path).append("/").append(fileinfo.name), files);//递归当前文件夹
}
}
else //文件处理
{
files.push_back(p.assign(path).append("/").append(fileinfo.name));//文件名
}
} while (_findnext(hFile, &fileinfo) == 0); //寻找下一个,成功返回0,否则-1
_findclose(hFile);
}
}
void SplitString(const string& s, vector<string>& v, const string& c)
{
string::size_type pos1, pos2;
pos2 = s.find(c);
pos1 = 0;
while (string::npos != pos2)
{
v.push_back(s.substr(pos1, pos2 - pos1));
pos1 = pos2 + c.size();
pos2 = s.find(c, pos1);
}
if (pos1 != s.length())
v.push_back(s.substr(pos1));
}
int main()
{
string DATA_DIR = "E:/WestRegion";
vector<string> files;
getAllFiles(DATA_DIR, files);//所有文件与文件夹的路径都输出
system("echo test");
for (int i=0;i<files.size();i++)
{
string InputFile = files[i];
string osgb = "osgb";
if (InputFile.find(osgb)!=-1)
{
vector<string> v1,v2;
SplitString(InputFile, v1, "/"); //可按多个字符来分隔;
string FileNameAll = v1[2];
SplitString(FileNameAll, v2, ".");
string FileName = v2[0];
string osgconv = "osgconv ";
string OutputFile = " E:/osgconvFinshed/" + FileName + ".obj";
string CommandLine = osgconv+InputFile+OutputFile;
system(CommandLine.c_str());
//system("pause");
}
}
return 0;
}
完成的操作是E:\WestRegion下的所有osgb文件转成obj文件储存在E:\osgconvFinished文件夹下。