Draw_extend使用OpenGL显示数据点
2016-01-12 16:22
375 查看
//alterload_map.dev //safetyverion2016/1/12 #include<iostream> #include<fstream> #include<vector> #include<stdlib.h> #include<sstream>//使用istringstream必须包含的头文件 #include<string> #include"string2num.hpp" #include"map.hpp" #include<windows.h> #include<GL/glut.h> usingnamespacestd; voidtest_map(){ unsignedintsum;doubleSa; doublenorth=polys[0]->north(); doublesouth=polys[0]->south(); doubleeast=polys[0]->east(); doublewest=polys[0]->west(); for(inti=0;i<polys.size();i++){ sum+=polys[i]->points.size(); Sa+=polys[i]->area(); } for(inti=0;i<polys.size();i++){ //比较每一个polygon的边界值,求出整个地图的四个边界值 if(polys[i]->north()>=north)north=polys[i]->north(); if(polys[i]->south()<=south)south=polys[i]->south(); if(polys[i]->east()>=east)east=polys[i]->east(); if(polys[i]->west()<=west)west=polys[i]->west(); } ofstreamout("map_para.txt"); if(out.is_open()) { out<<"mapparameter:\n"; out<<"countpolygon="<<polys.size()<<endl; out<<"size="<<sum<<endl; out<<"area="<<Sa<<endl; out<<"north="<<north<<endl; out<<"south="<<south<<endl; out<<"east="<<east<<endl; out<<"west="<<west<<endl; out.close(); } } voiddisplay(void) { glClear(GL_COLOR_BUFFER_BIT); //用蓝色色绘制各省边界 glColor3f(0.0,0.0,1.0); glPolygonMode(GL_BACK,GL_LINE); for(inti=0;i<polys.size();i++) { vector<MapPoint>points=polys[i]->points; glBegin(GL_LINE_STRIP); for(intj=0;j<points.size();j++) { glVertex3f(points[j].longitude,points[j].latitude,0.0); } glEnd(); } glFlush(); } voidinit(void) { //设置背景颜色 glClearColor(0,1.0,0,0.0); //初始化观察值 glMatrixMode(GL_PROJECTION);//将矩阵模式设为投影 glLoadIdentity();//对矩阵进行单位化 glOrtho(110.0,118.0,30.0,38.0,-1.0,1.0);//构造平行投影矩阵 } intmain(intargc,char*argv[]){ //数据文件请到http://files.cnblogs.com/opengl/HenanCounty.rar下载放到D盘根目录下并解压 stringfilename="HenanCounty.txt";//在当前工程目录下 //ReadData2num(filename); polys=ReadMapData(filename); test_map(); glutInit(&argc,argv); glutInitDisplayMode(GLUT_SINGLE|GLUT_RGB);//单缓存和RGB glutInitWindowSize(500,500); glutInitWindowPosition(100,100); glutCreateWindow("Map_henan"); init(); glutDisplayFunc(display);//显示回调函数 glutMainLoop(); return0; }
"HenanCounty.txt"是一份文本格式的地图:
单个整数代表点数(包含的点可能是某个省内市区的范围),整数n下面紧接着的数据行共有n行,是以经纬度表示的地理坐标。 程序运行结果:
关于地图的信息(多边形数目、总点数、面积、边界)通过test_map()函数写入map_para.txt
目前算得的面积还有问题,这通过边界值就可以看出来,这还有待解决。
string2num.hpp定义了模板函数用于字符串形式的数字向基本数值类型的转化(其实这个定义比较多余<sstream>里面定义的字符串处理类包含此功能)
#ifndef_STRING2NUM_HPP_
#define_STRING2NUM_HPP_
#include<sstream>//使用istringstream必须包含的头文件
#include<string>
usingnamespacestd;
//模板函数:将string类型变量转换为常用的数值类型bymaowei
template<classType>
TypestringToNum(conststring&str)
{
istringstreamiss(str);
Typenum;
iss>>num;
returnnum;
}
#endif
map.hpp包括了基本类的定义,这是在map_origin.cpp的基础上修改得到的,主要是增加了一些获取地图信息相关的函数。其中多边形容器的定义部分值得充分学习消化。
#ifndef_MAP_HPP_
#define_MAP_HPP_
#include<vector>
#include<math.h>
usingnamespacestd;
classMapPoint
{
public:
doublelongitude;//经度
doublelatitude;//纬度
MapPoint(){}
MapPoint(doublex,doubley){longitude=x;latitude=y;}
};
classMap
{
public:
intmapsize;
vector<MapPoint>points;//多边形的顶点序列
Map(){}
Map(inti){mapsize=i;}
};
//unsignedintcount,num;
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%translatefromorigin
classPolygon
{
public:
vector<MapPoint>points;//多边形的顶点序列
doublearea(void){
doubleA=0;unsignedintN=points.size();
for(inti=0;i<(N-1);i++){
A+=fabs(points[i].longitude*points[i+1].latitude-points[i].latitude*points[i+1].longitude);
}
A+=fabs(points[N-1].longitude*points[0].latitude-points[N-1].latitude*points[0].longitude);
returnA/2;
}
doublenorth(void){
doubleN=points[0].latitude;
for(inti=0;i<points.size();i++){if(points[i].latitude>=N)N=points[i].latitude;}
returnN;
}
doublesouth(void){
doubleS=points[0].latitude;
for(inti=0;i<points.size();i++){if(points[i].latitude<=S)S=points[i].latitude;}
returnS;
}
doubleeast(void){
doubleE=points[0].longitude;
for(inti=0;i<points.size();i++){if(points[i].longitude>=E)E=points[i].longitude;}
returnE;
}
doublewest(void){
doubleW=points[0].longitude;
for(inti=0;i<points.size();i++){if(points[i].longitude<=W)W=points[i].longitude;}
returnW;
}
};
vector<Polygon*>polys;//多边形集合
vector<Polygon*>ReadMapData(conststringfilename)
{
intPointCount;
vector<Polygon*>polygons;
ifstreamfs(filename.c_str());
while(fs.eof()!=true)
{
Polygon*poly=newPolygon;
fs>>PointCount;
//cout<<PointCount<<endl;
for(inti=0;i<PointCount;i++)
{
MapPointp;
fs>>p.longitude>>p.latitude;
poly->points.push_back(p);
}
polygons.push_back(poly);
}
returnpolygons;
}
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
MapReadData2num(conststringstr)//逐行读取并转化为常用数据类型bymememagic
{
cout<<"startreadmap"<<endl;
ifstreamfin(str.c_str());
if(!fin.is_open())
{cout<<"Erroropeningfile";exit(1);}
strings;MapImap;
intSize=0,i=0;boolflag;
while(getline(fin,s))
{
if(i==Size){ints_i=stringToNum<int>(s);Size=s_i+1;i=0;//count+=s_i;num++;
//cout<<"(vertexnum):"<<s_i<<endl;
}
else
{
istringstreamis(s);//采用istringstream从string对象str中读取字符
strings1;doublex,y;
while(is>>s1){
doubles_d=stringToNum<double>(s1);
if(!flag){x=s_d;flag=!flag;}
else{y=s_d;flag=!flag;}
//cout<<s_d<<'';
}
//cout<<"x="<<x<<''<<"y="<<y<<endl;
MapPointp(x,y);
Imap.points.push_back(p);
}
i++;
}
returnImap;
}
#endif
与Draw_v1相比,这个程序有了不少变化:数据来源不再靠手工在命令窗口输入,而是一个有确定“格式”的简单文本,数据量也较大,程序里面对数据的处理代码自然不同;多边形容器(vector<Polygon*>polys)是对图形(vector<Shape>)容器的拓展;利用OpenGL实现了数据的可视化(关于OpenGL绘图的原理有待进一步学习理解).
相关文章推荐
- centos7开机没有进入桌面gnome,kde
- Linux中的ls命令详解
- linux之FTP
- linux平台C++开发基本知识
- openwrt-how to compile
- Hadoop Maven pom文件示例
- Hadoop Maven pom文件示例
- 桌面气泡通知 (Desktop notifications )
- Sqoop操作实践
- Sqoop操作实践
- CentOS7下Firewall防火墙配置用法详解
- qt 版本和linux下字符编码问题
- OpenCV2:Mat属性type,depth,step
- .net网站报错:对象的当前状态使该操作无效
- xshell密钥登录和密钥登录注意
- YARN : Architecture of Next Generation Apache Hadoop MapReduceFramework
- docker run hello-world的工作流程
- ubuntu-14.04.3上单机安装hadoop2.6
- Nginx: error while loading shared libraries: libpcre.so.1解决
- 将Linux代码移植到Windows的简单方法