/** * Author : GĂ©rald FENOY * * Copyright 2009-2013 GeoLabs SARL. All rights reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: * * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN * THE SOFTWARE. */ #include #include #include #include #include #include #include #include "cpl_minixml.h" #include "ogr_api.h" #include "ogrsf_frmts.h" #include "service.h" typedef CGAL::Exact_predicates_inexact_constructions_kernel K; typedef CGAL::Delaunay_triangulation_2 Triangulation; typedef Triangulation::Edge_iterator Edge_iterator; typedef Triangulation::Point Point; typedef CGAL::Constrained_Delaunay_triangulation_2 CDT; typedef CDT::Point Point; typedef CDT::Vertex_handle Vertex_handle; typedef CGAL::Exact_predicates_inexact_constructions_kernel K; typedef CGAL::Triangulation_euclidean_traits_xy_3 Gt; typedef CGAL::Delaunay_triangulation_2 DelaunayTriangulation; typedef Triangulation::Vertex_circulator Vertex_circulator; typedef K::Point_3 Point1; extern "C" { #include #include #include #include #include #include #include #include #include xmlNodeSet* extractFromDoc(xmlDocPtr,char*); void printExceptionReportResponse(maps*,map*); int Voronoi(maps*& conf,maps*& inputs,maps*& outputs){ #ifdef DEBUG fprintf(stderr,"\nService internal print\nStarting\n"); #endif maps* cursor=inputs; OGRGeometryH geometry,res; int bufferDistance; xmlInitParser(); map* tmpm=NULL; tmpm=getMapFromMaps(inputs,"InputPoints","value"); xmlInitParser(); xmlDocPtr doc = xmlParseMemory(tmpm->value,strlen(tmpm->value)); xmlNodePtr cur = xmlDocGetRootElement(doc); /** * Parse every Input in DataInputs node. */ maps* tempMaps=NULL; xmlXPathContextPtr xpathCtx; xmlXPathObjectPtr xpathObj; xpathCtx = xmlXPathNewContext(doc); xpathObj = xmlXPathEvalExpression(BAD_CAST "/*/*[local-name()='featureMember']/*/*/*[local-name()='Point']/*[local-name()='coordinates']",xpathCtx); xmlXPathFreeContext(xpathCtx); xmlNodeSet* nSet=xpathObj->nodesetval; if(nSet==NULL){ setMapInMaps(conf,"lenv","message","Unable to continue !!!"); return SERVICE_FAILED; } char filepath[2048]; map* tmpMap=getMapFromMaps(conf,"main","tmpPath"); if(tmpMap!=NULL){ sprintf(filepath,"%s/varonoi_%d.tmp",tmpMap->value,getpid()); } FILE *fo=fopen(filepath,"w"); #ifdef DEBUG fprintf(stderr,"File Creation (%s) OK\nPrinting %d Points.\n",filepath,nSet->nodeNr); #endif for(int k=0;knodeNr;k++){ xmlNodePtr cur=nSet->nodeTab[k]; char *val= (char*)xmlNodeListGetString(doc,cur->xmlChildrenNode,1); char *tmp=strstr(val,","); char tmp1[1024]; strncpy(tmp1,val,strlen(val)-strlen(tmp)); tmp1[strlen(val)-strlen(tmp)]=0; char buff[1024]; sprintf(buff,"%s %s\n",tmp1,tmp+1); fwrite(buff,1,strlen(buff)*sizeof(char),fo); } fclose(fo); #ifdef DEBUG fprintf(stderr,"File Close (%s) OK\n",filepath); #endif std::ifstream in(filepath); std::istream_iterator begin(in); std::istream_iterator end; Triangulation T; T.insert(begin, end); OGRRegisterAll(); /* -------------------------------------------------------------------- */ /* Try opening the output datasource as an existing, writable */ /* -------------------------------------------------------------------- */ OGRDataSource *poODS; OGRSFDriverRegistrar *poR = OGRSFDriverRegistrar::GetRegistrar(); OGRSFDriver *poDriver = NULL; int iDriver; tmpMap=getMapFromMaps(outputs,"Result","mimeType"); const char *oDriver; oDriver="GeoJSON"; if(tmpMap!=NULL){ if(strcmp(tmpMap->value,"text/xml")==0){ oDriver="GML"; } } for( iDriver = 0; iDriver < poR->GetDriverCount() && poDriver == NULL; iDriver++ ) { #ifdef DEBUG fprintf(stderr,"D:%s\n",poR->GetDriver(iDriver)->GetName()); #endif if( EQUAL(poR->GetDriver(iDriver)->GetName(),oDriver) ) { poDriver = poR->GetDriver(iDriver); } } if( poDriver == NULL ) { char emessage[8192]; sprintf( emessage, "Unable to find driver `%s'.\n", oDriver ); sprintf( emessage, "%sThe following drivers are available:\n",emessage ); for( iDriver = 0; iDriver < poR->GetDriverCount(); iDriver++ ) { sprintf( emessage, "%s -> `%s'\n", emessage, poR->GetDriver(iDriver)->GetName() ); } setMapInMaps(conf,"lenv","message",emessage); return SERVICE_FAILED; } if( !poDriver->TestCapability( ODrCCreateDataSource ) ){ char emessage[1024]; sprintf( emessage, "%s driver does not support data source creation.\n", "json" ); setMapInMaps(conf,"lenv","message",emessage); return SERVICE_FAILED; } /* -------------------------------------------------------------------- */ /* Create the output data source. */ /* -------------------------------------------------------------------- */ map* tpath=getMapFromMaps(conf,"main","tmpPath"); char *pszDestDataSource=(char*)malloc(strlen(tpath->value)+20); char **papszDSCO=NULL; sprintf(pszDestDataSource,"%s/result_%d.json",tpath->value,getpid()); poODS = poDriver->CreateDataSource( pszDestDataSource, papszDSCO ); if( poODS == NULL ){ char emessage[1024]; sprintf( emessage, "%s driver failed to create %s\n", "json", pszDestDataSource ); setMapInMaps(conf,"lenv","message",emessage); return SERVICE_FAILED; } /* -------------------------------------------------------------------- */ /* Create the layer. */ /* -------------------------------------------------------------------- */ if( !poODS->TestCapability( ODsCCreateLayer ) ) { char emessage[1024]; sprintf( emessage, "Layer %s not found, and CreateLayer not supported by driver.", "Result" ); setMapInMaps(conf,"lenv","message",emessage); return SERVICE_FAILED; } CPLErrorReset(); OGRLayer *poDstLayer = poODS->CreateLayer( "Result", NULL,wkbLineString,NULL); if( poDstLayer == NULL ){ setMapInMaps(conf,"lenv","message","Layer creation failed.\n"); return SERVICE_FAILED; } int ns = 0; int nr = 0; Edge_iterator eit =T.edges_begin(); for ( ; eit !=T.edges_end(); ++eit) { CGAL::Object o = T.dual(eit); if (const K::Segment_2 *tmp=CGAL::object_cast(&o)) { const K::Point_2 p1=tmp->source(); const K::Point_2 p2=tmp->target(); #ifdef DEBUG fprintf(stderr,"P1 %d %d | P2 %d %d\n",p1.x(),p1.y(),p2.x(),p2.y()); #endif OGRFeatureH hFeature = OGR_F_Create( OGR_L_GetLayerDefn( poDstLayer ) ); OGRGeometryH currLine=OGR_G_CreateGeometry(wkbLineString); OGR_G_AddPoint_2D(currLine,p1.x(),p1.y()); OGR_G_AddPoint_2D(currLine,p2.x(),p2.y()); OGR_F_SetGeometry( hFeature, currLine ); OGR_G_DestroyGeometry(currLine); if( OGR_L_CreateFeature( poDstLayer, hFeature ) != OGRERR_NONE ){ setMapInMaps(conf,"lenv","message","Failed to create feature in file.\n"); return SERVICE_FAILED; } OGR_F_Destroy( hFeature ); ++ns ; } else if (CGAL::object_cast(&o)) {++nr;} } OGR_DS_Destroy( poODS ); OGRCleanupAll(); #ifdef DEBUG std::cerr << "The Voronoi diagram has " << ns << " finite edges " << " and " << nr << " rays" << std::endl; sprintf(tmp1,"%d finite edges, %d rays",ns,nr); #endif char tmp1[1024]; FILE * fichier=fopen(pszDestDataSource,"r"); struct stat file_status; stat(pszDestDataSource, &file_status); char *res1=(char *)malloc(file_status.st_size*sizeof(char)); if(fichier==NULL){ char tmp[1024]; sprintf(tmp,"Failed to open file %s for reading purpose.\n", pszDestDataSource); setMapInMaps(conf,"lenv","message",tmp); return SERVICE_FAILED; } fread(res1,1,(file_status.st_size)*sizeof(char),fichier); res1[strlen(res1)]=0; fclose(fichier); unlink(pszDestDataSource); setMapInMaps(outputs,"Result","value",res1); if(strcmp(oDriver,"GML")==0) setMapInMaps(outputs,"Result","mimeType","text/xml"); else setMapInMaps(outputs,"Result","mimeType","text/plain"); setMapInMaps(outputs,"Result","encoding","UTF-8"); #ifdef DEBUG fprintf(stderr,"\nService internal print\n===\n"); #endif xmlCleanupParser(); return SERVICE_SUCCEEDED; } }