Cesium批量显示三维模型(gltf格式)和一些心得体会——接上篇

上篇是关于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文件夹下。



发布了6 篇原创文章 · 获赞 14 · 访问量 2万+
展开阅读全文

没有更多推荐了,返回首页

©️2019 CSDN 皮肤主题: 大白 设计师: CSDN官方博客

分享到微信朋友圈

×

扫一扫,手机浏览