-: 0:Source:lwline.c -: 0:Programs:129 -: 1:/********************************************************************** -: 2: * -: 3: * PostGIS - Spatial Types for PostgreSQL -: 4: * http://postgis.net -: 5: * -: 6: * PostGIS is free software: you can redistribute it and/or modify -: 7: * it under the terms of the GNU General Public License as published by -: 8: * the Free Software Foundation, either version 2 of the License, or -: 9: * (at your option) any later version. -: 10: * -: 11: * PostGIS is distributed in the hope that it will be useful, -: 12: * but WITHOUT ANY WARRANTY; without even the implied warranty of -: 13: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -: 14: * GNU General Public License for more details. -: 15: * -: 16: * You should have received a copy of the GNU General Public License -: 17: * along with PostGIS. If not, see . -: 18: * -: 19: ********************************************************************** -: 20: * -: 21: * Copyright (C) 2012 Sandro Santilli -: 22: * Copyright (C) 2001-2006 Refractions Research Inc. -: 23: * -: 24: **********************************************************************/ -: 25: -: 26: -: 27:/* basic LWLINE functions */ -: 28: -: 29:#include -: 30:#include -: 31:#include -: 32:#include "liblwgeom_internal.h" -: 33:#include "lwgeom_log.h" -: 34: -: 35: -: 36: -: 37:/* -: 38: * Construct a new LWLINE. points will *NOT* be copied -: 39: * use SRID=SRID_UNKNOWN for unknown SRID (will have 8bit type's S = 0) -: 40: */ -: 41:LWLINE * function lwline_construct called 606012 returned 100% blocks executed 100% 606012: 42:lwline_construct(int srid, GBOX *bbox, POINTARRAY *points) -: 43:{ -: 44: LWLINE *result; 606012: 45: result = (LWLINE*) lwalloc(sizeof(LWLINE)); call 0 returned 100% -: 46: -: 47: LWDEBUG(2, "lwline_construct called."); -: 48: 606012: 49: result->type = LINETYPE; -: 50: 606012: 51: result->flags = points->flags; 606012: 52: FLAGS_SET_BBOX(result->flags, bbox?1:0); branch 0 taken 1% (fallthrough) branch 1 taken 99% -: 53: -: 54: LWDEBUGF(3, "lwline_construct type=%d", result->type); -: 55: 606012: 56: result->srid = srid; 606012: 57: result->points = points; 606012: 58: result->bbox = bbox; -: 59: 606012: 60: return result; -: 61:} -: 62: -: 63:LWLINE * function lwline_construct_empty called 9574 returned 100% blocks executed 100% 9574: 64:lwline_construct_empty(int srid, char hasz, char hasm) -: 65:{ 9574: 66: LWLINE *result = lwalloc(sizeof(LWLINE)); call 0 returned 100% 9574: 67: result->type = LINETYPE; 9574: 68: result->flags = gflags(hasz,hasm,0); call 0 returned 100% 9574: 69: result->srid = srid; 9574: 70: result->points = ptarray_construct_empty(hasz, hasm, 1); call 0 returned 100% 9574: 71: result->bbox = NULL; 9574: 72: return result; -: 73:} -: 74: -: 75: function lwline_free called 5989758 returned 100% blocks executed 88% 5989758: 76:void lwline_free (LWLINE *line) -: 77:{ 5989758*: 78: if ( ! line ) return; branch 0 taken 0% (fallthrough) branch 1 taken 100% -: 79: 5989758: 80: if ( line->bbox ) branch 0 taken 9% (fallthrough) branch 1 taken 91% 517980: 81: lwfree(line->bbox); call 0 returned 100% 5989758: 82: if ( line->points ) branch 0 taken 100% (fallthrough) branch 1 taken 0% 5989758: 83: ptarray_free(line->points); call 0 returned 100% 5989758: 84: lwfree(line); call 0 returned 100% -: 85:} -: 86: -: 87: function printLWLINE called 0 returned 0% blocks executed 0% #####: 88:void printLWLINE(LWLINE *line) -: 89:{ #####: 90: lwnotice("LWLINE {"); call 0 never executed #####: 91: lwnotice(" ndims = %i", (int)FLAGS_NDIMS(line->flags)); call 0 never executed #####: 92: lwnotice(" srid = %i", (int)line->srid); call 0 never executed #####: 93: printPA(line->points); call 0 never executed #####: 94: lwnotice("}"); call 0 never executed #####: 95:} -: 96: -: 97:/* @brief Clone LWLINE object. Serialized point lists are not copied. -: 98: * -: 99: * @see ptarray_clone -: 100: */ -: 101:LWLINE * function lwline_clone called 5852 returned 100% blocks executed 100% 5852: 102:lwline_clone(const LWLINE *g) -: 103:{ 5852: 104: LWLINE *ret = lwalloc(sizeof(LWLINE)); call 0 returned 100% -: 105: -: 106: LWDEBUGF(2, "lwline_clone called with %p", g); -: 107: 5852: 108: memcpy(ret, g, sizeof(LWLINE)); -: 109: 5852: 110: ret->points = ptarray_clone(g->points); call 0 returned 100% -: 111: 5852: 112: if ( g->bbox ) ret->bbox = gbox_copy(g->bbox); branch 0 taken 1% (fallthrough) branch 1 taken 99% call 2 returned 100% 5852: 113: return ret; -: 114:} -: 115: -: 116:/* Deep clone LWLINE object. POINTARRAY *is* copied. */ -: 117:LWLINE * function lwline_clone_deep called 22418 returned 100% blocks executed 100% 22418: 118:lwline_clone_deep(const LWLINE *g) -: 119:{ 22418: 120: LWLINE *ret = lwalloc(sizeof(LWLINE)); call 0 returned 100% -: 121: -: 122: LWDEBUGF(2, "lwline_clone_deep called with %p", g); 22418: 123: memcpy(ret, g, sizeof(LWLINE)); -: 124: 22418: 125: if ( g->bbox ) ret->bbox = gbox_copy(g->bbox); branch 0 taken 21% (fallthrough) branch 1 taken 79% call 2 returned 100% 22418: 126: if ( g->points ) ret->points = ptarray_clone_deep(g->points); branch 0 taken 100% (fallthrough) branch 1 taken 0% call 2 returned 100% 22418: 127: FLAGS_SET_READONLY(ret->flags,0); -: 128: 22418: 129: return ret; -: 130:} -: 131: -: 132: -: 133:void function lwline_release called 2 returned 100% blocks executed 100% 2: 134:lwline_release(LWLINE *lwline) -: 135:{ 2: 136: lwgeom_release(lwline_as_lwgeom(lwline)); call 0 returned 100% call 1 returned 100% 2: 137:} -: 138: -: 139: -: 140:LWLINE * function lwline_segmentize2d called 866 returned 100% blocks executed 80% 866: 141:lwline_segmentize2d(const LWLINE *line, double dist) -: 142:{ 866: 143: POINTARRAY *segmentized = ptarray_segmentize2d(line->points, dist); call 0 returned 100% 866*: 144: if ( ! segmentized ) return NULL; branch 0 taken 0% (fallthrough) branch 1 taken 100% 866: 145: return lwline_construct(line->srid, NULL, segmentized); call 0 returned 100% -: 146:} -: 147: -: 148:/* check coordinate equality */ -: 149:char function lwline_same called 210 returned 100% blocks executed 100% 210: 150:lwline_same(const LWLINE *l1, const LWLINE *l2) -: 151:{ 210: 152: return ptarray_same(l1->points, l2->points); call 0 returned 100% -: 153:} -: 154: -: 155:/* -: 156: * Construct a LWLINE from an array of point and line geometries -: 157: * LWLINE dimensions are large enough to host all input dimensions. -: 158: */ -: 159:LWLINE * function lwline_from_lwgeom_array called 2608 returned 100% blocks executed 83% 2608: 160:lwline_from_lwgeom_array(int srid, uint32_t ngeoms, LWGEOM **geoms) -: 161:{ -: 162: uint32_t i; 2608: 163: int hasz = LW_FALSE; 2608: 164: int hasm = LW_FALSE; -: 165: POINTARRAY *pa; -: 166: LWLINE *line; -: 167: POINT4D pt; -: 168: LWPOINTITERATOR* it; -: 169: -: 170: /* -: 171: * Find output dimensions, check integrity -: 172: */ 36794: 173: for (i=0; iflags) ) hasz = LW_TRUE; branch 0 taken 1% (fallthrough) branch 1 taken 99% 34186: 176: if ( FLAGS_GET_M(geoms[i]->flags) ) hasm = LW_TRUE; branch 0 taken 1% (fallthrough) branch 1 taken 99% 34186*: 177: if ( hasz && hasm ) break; /* Nothing more to learn! */ branch 0 taken 1% (fallthrough) branch 1 taken 99% branch 2 taken 0% (fallthrough) branch 3 taken 100% -: 178: } -: 179: -: 180: /* -: 181: * ngeoms should be a guess about how many points we have in input. -: 182: * It's an underestimate for lines and multipoints */ 2608: 183: pa = ptarray_construct_empty(hasz, hasm, ngeoms); call 0 returned 100% -: 184: 36794: 185: for ( i=0; i < ngeoms; i++ ) branch 0 taken 93% branch 1 taken 7% (fallthrough) -: 186: { 34186: 187: LWGEOM *g = geoms[i]; -: 188: 34186: 189: if ( lwgeom_is_empty(g) ) continue; call 0 returned 100% branch 1 taken 1% (fallthrough) branch 2 taken 99% -: 190: 34184: 191: if ( g->type == POINTTYPE ) branch 0 taken 99% (fallthrough) branch 1 taken 1% -: 192: { 34164: 193: lwpoint_getPoint4d_p((LWPOINT*)g, &pt); call 0 returned 100% 34164: 194: ptarray_append_point(pa, &pt, LW_TRUE); call 0 returned 100% -: 195: } 20: 196: else if ( g->type == LINETYPE ) branch 0 taken 90% (fallthrough) branch 1 taken 10% -: 197: { -: 198: /* -: 199: * Append the new line points, de-duplicating against the previous points. -: 200: * Duplicated points internal to the linestring are untouched. -: 201: */ 18: 202: ptarray_append_ptarray(pa, ((LWLINE*)g)->points, -1); call 0 returned 100% -: 203: } 2: 204: else if ( g->type == MULTIPOINTTYPE ) branch 0 taken 100% (fallthrough) branch 1 taken 0% -: 205: { 2: 206: it = lwpointiterator_create(g); call 0 returned 100% 10: 207: while(lwpointiterator_next(it, &pt)) call 0 returned 100% branch 1 taken 80% branch 2 taken 20% (fallthrough) -: 208: { 8: 209: ptarray_append_point(pa, &pt, LW_TRUE); call 0 returned 100% -: 210: } 2: 211: lwpointiterator_destroy(it); call 0 returned 100% -: 212: } -: 213: else -: 214: { #####: 215: ptarray_free(pa); call 0 never executed #####: 216: lwerror("lwline_from_ptarray: invalid input type: %s", lwtype_name(g->type)); call 0 never executed call 1 never executed #####: 217: return NULL; -: 218: } -: 219: } -: 220: 2608: 221: if ( pa->npoints > 0 ) branch 0 taken 100% (fallthrough) branch 1 taken 0% 2608: 222: line = lwline_construct(srid, NULL, pa); call 0 returned 100% -: 223: else { -: 224: /* Is this really any different from the above ? */ #####: 225: ptarray_free(pa); call 0 never executed #####: 226: line = lwline_construct_empty(srid, hasz, hasm); call 0 never executed -: 227: } -: 228: 2608: 229: return line; -: 230:} -: 231: -: 232:/* -: 233: * Construct a LWLINE from an array of LWPOINTs -: 234: * LWLINE dimensions are large enough to host all input dimensions. -: 235: */ -: 236:LWLINE * function lwline_from_ptarray called 560548 returned 100% blocks executed 79% 560548: 237:lwline_from_ptarray(int srid, uint32_t npoints, LWPOINT **points) -: 238:{ -: 239: uint32_t i; 560548: 240: int hasz = LW_FALSE; 560548: 241: int hasm = LW_FALSE; -: 242: POINTARRAY *pa; -: 243: LWLINE *line; -: 244: POINT4D pt; -: 245: -: 246: /* -: 247: * Find output dimensions, check integrity -: 248: */ 1681644: 249: for (i=0; itype != POINTTYPE ) branch 0 taken 0% (fallthrough) branch 1 taken 100% -: 252: { #####: 253: lwerror("lwline_from_ptarray: invalid input type: %s", lwtype_name(points[i]->type)); call 0 never executed call 1 never executed #####: 254: return NULL; -: 255: } 1121096: 256: if ( FLAGS_GET_Z(points[i]->flags) ) hasz = LW_TRUE; branch 0 taken 99% (fallthrough) branch 1 taken 1% 1121096*: 257: if ( FLAGS_GET_M(points[i]->flags) ) hasm = LW_TRUE; branch 0 taken 0% (fallthrough) branch 1 taken 100% 1121096*: 258: if ( hasz && hasm ) break; /* Nothing more to learn! */ branch 0 taken 99% (fallthrough) branch 1 taken 1% branch 2 taken 0% (fallthrough) branch 3 taken 100% -: 259: } -: 260: 560548: 261: pa = ptarray_construct_empty(hasz, hasm, npoints); call 0 returned 100% -: 262: 1681644: 263: for ( i=0; i < npoints; i++ ) branch 0 taken 67% branch 1 taken 33% (fallthrough) -: 264: { 1121096: 265: if ( ! lwpoint_is_empty(points[i]) ) call 0 returned 100% branch 1 taken 100% (fallthrough) branch 2 taken 0% -: 266: { 1121096: 267: lwpoint_getPoint4d_p(points[i], &pt); call 0 returned 100% 1121096: 268: ptarray_append_point(pa, &pt, LW_TRUE); call 0 returned 100% -: 269: } -: 270: } -: 271: 560548: 272: if ( pa->npoints > 0 ) branch 0 taken 100% (fallthrough) branch 1 taken 0% 560548: 273: line = lwline_construct(srid, NULL, pa); call 0 returned 100% -: 274: else #####: 275: line = lwline_construct_empty(srid, hasz, hasm); call 0 never executed -: 276: 560548: 277: return line; -: 278:} -: 279: -: 280:/* -: 281: * Construct a LWLINE from a LWMPOINT -: 282: */ -: 283:LWLINE * function lwline_from_lwmpoint called 6 returned 100% blocks executed 87% 6: 284:lwline_from_lwmpoint(int srid, const LWMPOINT *mpoint) -: 285:{ -: 286: uint32_t i; 6: 287: POINTARRAY *pa = NULL; 6: 288: LWGEOM *lwgeom = (LWGEOM*)mpoint; -: 289: POINT4D pt; -: 290: 6: 291: char hasz = lwgeom_has_z(lwgeom); call 0 returned 100% 6: 292: char hasm = lwgeom_has_m(lwgeom); call 0 returned 100% 6: 293: uint32_t npoints = mpoint->ngeoms; -: 294: 6: 295: if ( lwgeom_is_empty(lwgeom) ) call 0 returned 100% branch 1 taken 0% (fallthrough) branch 2 taken 100% -: 296: { #####: 297: return lwline_construct_empty(srid, hasz, hasm); call 0 never executed -: 298: } -: 299: 6: 300: pa = ptarray_construct(hasz, hasm, npoints); call 0 returned 100% -: 301: 20: 302: for (i=0; i < npoints; i++) branch 0 taken 70% branch 1 taken 30% (fallthrough) -: 303: { 14: 304: getPoint4d_p(mpoint->geoms[i]->point, 0, &pt); call 0 returned 100% 14: 305: ptarray_set_point4d(pa, i, &pt); call 0 returned 100% -: 306: } -: 307: -: 308: LWDEBUGF(3, "lwline_from_lwmpoint: constructed pointarray for %d points", mpoint->ngeoms); -: 309: 6: 310: return lwline_construct(srid, NULL, pa); call 0 returned 100% -: 311:} -: 312: -: 313:/** -: 314:* Returns freshly allocated #LWPOINT that corresponds to the index where. -: 315:* Returns NULL if the geometry is empty or the index invalid. -: 316:*/ -: 317:LWPOINT* function lwline_get_lwpoint called 33782 returned 100% blocks executed 100% 33782: 318:lwline_get_lwpoint(const LWLINE *line, uint32_t where) -: 319:{ -: 320: POINT4D pt; -: 321: LWPOINT *lwpoint; -: 322: POINTARRAY *pa; -: 323: 33782: 324: if ( lwline_is_empty(line) || where >= line->points->npoints ) call 0 returned 100% branch 1 taken 100% (fallthrough) branch 2 taken 0% branch 3 taken 1% (fallthrough) branch 4 taken 99% 18: 325: return NULL; -: 326: 33764: 327: pa = ptarray_construct_empty(FLAGS_GET_Z(line->flags), FLAGS_GET_M(line->flags), 1); call 0 returned 100% 33764: 328: pt = getPoint4d(line->points, where); call 0 returned 100% 33764: 329: ptarray_append_point(pa, &pt, LW_TRUE); call 0 returned 100% 33764: 330: lwpoint = lwpoint_construct(line->srid, NULL, pa); call 0 returned 100% 33764: 331: return lwpoint; -: 332:} -: 333: -: 334: -: 335:int function lwline_add_lwpoint called 0 returned 0% blocks executed 0% #####: 336:lwline_add_lwpoint(LWLINE *line, LWPOINT *point, uint32_t where) -: 337:{ -: 338: POINT4D pt; #####: 339: getPoint4d_p(point->point, 0, &pt); call 0 never executed -: 340: #####: 341: if ( ptarray_insert_point(line->points, &pt, where) != LW_SUCCESS ) call 0 never executed branch 1 never executed branch 2 never executed #####: 342: return LW_FAILURE; -: 343: -: 344: /* Update the bounding box */ #####: 345: if ( line->bbox ) branch 0 never executed branch 1 never executed -: 346: { #####: 347: lwgeom_refresh_bbox((LWGEOM*)line); call 0 never executed -: 348: } -: 349: #####: 350: return LW_SUCCESS; -: 351:} -: 352: -: 353: -: 354: -: 355:LWLINE * function lwline_removepoint called 20 returned 100% blocks executed 100% 20: 356:lwline_removepoint(LWLINE *line, uint32_t index) -: 357:{ -: 358: POINTARRAY *newpa; -: 359: LWLINE *ret; -: 360: 20: 361: newpa = ptarray_removePoint(line->points, index); call 0 returned 100% -: 362: 20: 363: ret = lwline_construct(line->srid, NULL, newpa); call 0 returned 100% 20: 364: lwgeom_add_bbox((LWGEOM *) ret); call 0 returned 100% -: 365: 20: 366: return ret; -: 367:} -: 368: -: 369:/* -: 370: * Note: input will be changed, make sure you have permissions for this. -: 371: */ -: 372:void function lwline_setPoint4d called 46 returned 100% blocks executed 100% 46: 373:lwline_setPoint4d(LWLINE *line, uint32_t index, POINT4D *newpoint) -: 374:{ 46: 375: ptarray_set_point4d(line->points, index, newpoint); call 0 returned 100% -: 376: /* Update the box, if there is one to update */ 46: 377: if ( line->bbox ) branch 0 taken 39% (fallthrough) branch 1 taken 61% -: 378: { 18: 379: lwgeom_refresh_bbox((LWGEOM*)line); call 0 returned 100% -: 380: } 46: 381:} -: 382: -: 383:/** -: 384:* Re-write the measure ordinate (or add one, if it isn't already there) interpolating -: 385:* the measure between the supplied start and end values. -: 386:*/ -: 387:LWLINE* function lwline_measured_from_lwline called 420 returned 100% blocks executed 86% 420: 388:lwline_measured_from_lwline(const LWLINE *lwline, double m_start, double m_end) -: 389:{ 420: 390: int i = 0; 420: 391: int hasm = 0, hasz = 0; 420: 392: int npoints = 0; 420: 393: double length = 0.0; 420: 394: double length_so_far = 0.0; 420: 395: double m_range = m_end - m_start; -: 396: double m; 420: 397: POINTARRAY *pa = NULL; -: 398: POINT3DZ p1, p2; -: 399: 420: 400: if ( lwline->type != LINETYPE ) branch 0 taken 0% (fallthrough) branch 1 taken 100% -: 401: { #####: 402: lwerror("lwline_construct_from_lwline: only line types supported"); call 0 never executed #####: 403: return NULL; -: 404: } -: 405: 420: 406: hasz = FLAGS_GET_Z(lwline->flags); 420: 407: hasm = 1; -: 408: -: 409: /* Null points or npoints == 0 will result in empty return geometry */ 420: 410: if ( lwline->points ) branch 0 taken 100% (fallthrough) branch 1 taken 0% -: 411: { 420: 412: npoints = lwline->points->npoints; 420: 413: length = ptarray_length_2d(lwline->points); call 0 returned 100% 420: 414: getPoint3dz_p(lwline->points, 0, &p1); call 0 returned 100% -: 415: } -: 416: 420: 417: pa = ptarray_construct(hasz, hasm, npoints); call 0 returned 100% -: 418: 8902: 419: for ( i = 0; i < npoints; i++ ) branch 0 taken 95% branch 1 taken 5% (fallthrough) -: 420: { -: 421: POINT4D q; -: 422: POINT2D a, b; 8482: 423: getPoint3dz_p(lwline->points, i, &p2); call 0 returned 100% 8482: 424: a.x = p1.x; 8482: 425: a.y = p1.y; 8482: 426: b.x = p2.x; 8482: 427: b.y = p2.y; 8482: 428: length_so_far += distance2d_pt_pt(&a, &b); call 0 returned 100% 8482: 429: if ( length > 0.0 ) branch 0 taken 99% (fallthrough) branch 1 taken 1% 8478: 430: m = m_start + m_range * length_so_far / length; -: 431: /* #3172, support (valid) zero-length inputs */ 4: 432: else if ( length == 0.0 && npoints > 1 ) branch 0 taken 100% (fallthrough) branch 1 taken 0% branch 2 taken 100% (fallthrough) branch 3 taken 0% 4: 433: m = m_start + m_range * i / (npoints-1); -: 434: else #####: 435: m = 0.0; 8482: 436: q.x = p2.x; 8482: 437: q.y = p2.y; 8482: 438: q.z = p2.z; 8482: 439: q.m = m; 8482: 440: ptarray_set_point4d(pa, i, &q); call 0 returned 100% 8482: 441: p1 = p2; -: 442: } -: 443: 420: 444: return lwline_construct(lwline->srid, NULL, pa); call 0 returned 100% -: 445:} -: 446: -: 447:LWGEOM* function lwline_remove_repeated_points called 504 returned 100% blocks executed 100% 504: 448:lwline_remove_repeated_points(const LWLINE *lwline, double tolerance) -: 449:{ 504: 450: return lwgeom_remove_repeated_points((LWGEOM*)lwline, tolerance); call 0 returned 100% -: 451:} -: 452: -: 453:int function lwline_is_closed called 162 returned 100% blocks executed 100% 162: 454:lwline_is_closed(const LWLINE *line) -: 455:{ 162: 456: if (FLAGS_GET_Z(line->flags)) branch 0 taken 57% (fallthrough) branch 1 taken 43% 92: 457: return ptarray_is_closed_3d(line->points); call 0 returned 100% -: 458: 70: 459: return ptarray_is_closed_2d(line->points); call 0 returned 100% -: 460:} -: 461: -: 462:int function lwline_is_trajectory called 14 returned 100% blocks executed 100% 14: 463:lwline_is_trajectory(const LWLINE *line) -: 464:{ -: 465: POINT3DM p; -: 466: int i, n; 14: 467: double m = -1 * FLT_MAX; -: 468: 14: 469: if ( ! FLAGS_GET_M(line->flags) ) { branch 0 taken 14% (fallthrough) branch 1 taken 86% 2: 470: lwnotice("Line does not have M dimension"); call 0 returned 100% 2: 471: return LW_FALSE; -: 472: } -: 473: 12: 474: n = line->points->npoints; 12: 475: if ( n < 2 ) return LW_TRUE; /* empty or single-point are "good" */ branch 0 taken 17% (fallthrough) branch 1 taken 83% -: 476: 30: 477: for (i=0; ipoints, i, &p); call 0 returned 100% 26: 479: if ( p.m <= m ) { branch 0 taken 23% (fallthrough) branch 1 taken 77% 6: 480: lwnotice("Measure of vertex %d (%g) not bigger than measure of vertex %d (%g)", call 0 returned 100% -: 481: i, p.m, i-1, m); 6: 482: return LW_FALSE; -: 483: } 20: 484: m = p.m; -: 485: } -: 486: 4: 487: return LW_TRUE; -: 488:} -: 489: -: 490: -: 491:LWLINE* function lwline_force_dims called 840 returned 100% blocks executed 100% 840: 492:lwline_force_dims(const LWLINE *line, int hasz, int hasm) -: 493:{ 840: 494: POINTARRAY *pdims = NULL; -: 495: LWLINE *lineout; -: 496: -: 497: /* Return 2D empty */ 840: 498: if( lwline_is_empty(line) ) call 0 returned 100% branch 1 taken 4% (fallthrough) branch 2 taken 96% -: 499: { 36: 500: lineout = lwline_construct_empty(line->srid, hasz, hasm); call 0 returned 100% -: 501: } -: 502: else -: 503: { 804: 504: pdims = ptarray_force_dims(line->points, hasz, hasm); call 0 returned 100% 804: 505: lineout = lwline_construct(line->srid, NULL, pdims); call 0 returned 100% -: 506: } 840: 507: lineout->type = line->type; 840: 508: return lineout; -: 509:} -: 510: function lwline_count_vertices called 546118 returned 100% blocks executed 67% 546118: 511:uint32_t lwline_count_vertices(LWLINE *line) -: 512:{ 546118*: 513: assert(line); branch 0 taken 0% (fallthrough) branch 1 taken 100% call 2 never executed 546118: 514: if ( ! line->points ) branch 0 taken 0% (fallthrough) branch 1 taken 100% #####: 515: return 0; 546118: 516: return line->points->npoints; -: 517:} -: 518: function lwline_length called 560318 returned 100% blocks executed 80% 560318: 519:double lwline_length(const LWLINE *line) -: 520:{ 560318: 521: if ( lwline_is_empty(line) ) call 0 returned 100% branch 1 taken 0% (fallthrough) branch 2 taken 100% #####: 522: return 0.0; 560318: 523: return ptarray_length(line->points); call 0 returned 100% -: 524:} -: 525: function lwline_length_2d called 1128 returned 100% blocks executed 100% 1128: 526:double lwline_length_2d(const LWLINE *line) -: 527:{ 1128: 528: if ( lwline_is_empty(line) ) call 0 returned 100% branch 1 taken 1% (fallthrough) branch 2 taken 99% 4: 529: return 0.0; 1124: 530: return ptarray_length_2d(line->points); call 0 returned 100% -: 531:} -: 532: -: 533: function lwline_interpolate_points called 776 returned 100% blocks executed 93% 776: 534:POINTARRAY* lwline_interpolate_points(const LWLINE *line, double length_fraction, char repeat) { -: 535: POINT4D pt; -: 536: uint32_t i; -: 537: uint32_t points_to_interpolate; 776: 538: uint32_t points_found = 0; -: 539: double length; 776: 540: double length_fraction_increment = length_fraction; 776: 541: double length_fraction_consumed = 0; 776: 542: char has_z = (char) lwgeom_has_z(lwline_as_lwgeom(line)); call 0 returned 100% call 1 returned 100% 776: 543: char has_m = (char) lwgeom_has_m(lwline_as_lwgeom(line)); call 0 returned 100% call 1 returned 100% 776: 544: const POINTARRAY* ipa = line->points; -: 545: POINTARRAY* opa; -: 546: -: 547: /* Empty.InterpolatePoint == Point Empty */ 776: 548: if ( lwline_is_empty(line) ) call 0 returned 100% branch 1 taken 1% (fallthrough) branch 2 taken 99% -: 549: { 4: 550: return ptarray_construct_empty(has_z, has_m, 0); call 0 returned 100% -: 551: } -: 552: -: 553: /* If distance is one of the two extremes, return the point on that -: 554: * end rather than doing any computations -: 555: */ 772: 556: if ( length_fraction == 0.0 || length_fraction == 1.0 ) branch 0 taken 99% (fallthrough) branch 1 taken 1% branch 2 taken 0% (fallthrough) branch 3 taken 100% -: 557: { 2: 558: if ( length_fraction == 0.0 ) branch 0 taken 100% (fallthrough) branch 1 taken 0% 2: 559: getPoint4d_p(ipa, 0, &pt); call 0 returned 100% -: 560: else #####: 561: getPoint4d_p(ipa, ipa->npoints-1, &pt); call 0 never executed -: 562: 2: 563: opa = ptarray_construct(has_z, has_m, 1); call 0 returned 100% 2: 564: ptarray_set_point4d(opa, 0, &pt); call 0 returned 100% -: 565: 2: 566: return opa; -: 567: } -: 568: -: 569: /* Interpolate points along the line */ 770: 570: length = ptarray_length_2d(ipa); call 0 returned 100% 770: 571: points_to_interpolate = repeat ? (uint32_t) floor(1 / length_fraction) : 1; branch 0 taken 1% (fallthrough) branch 1 taken 99% 770: 572: opa = ptarray_construct(has_z, has_m, points_to_interpolate); call 0 returned 100% -: 573: 770: 574: const POINT2D* p1 = getPoint2d_cp(ipa, 0); call 0 returned 100% 1822: 575: for ( i = 0; i < ipa->npoints - 1 && points_found < points_to_interpolate; i++ ) branch 0 taken 63% (fallthrough) branch 1 taken 37% branch 2 taken 91% branch 3 taken 9% (fallthrough) -: 576: { 1052: 577: const POINT2D* p2 = getPoint2d_cp(ipa, i+1); call 0 returned 100% 1052: 578: double segment_length_frac = distance2d_pt_pt(p1, p2) / length; call 0 returned 100% -: 579: -: 580: /* If our target distance is before the total length we've seen -: 581: * so far. create a new point some distance down the current -: 582: * segment. -: 583: */ 1826: 584: while ( length_fraction < length_fraction_consumed + segment_length_frac && points_found < points_to_interpolate ) branch 0 taken 62% (fallthrough) branch 1 taken 38% branch 2 taken 68% branch 3 taken 32% (fallthrough) -: 585: { 774: 586: POINT4D p1_4d = getPoint4d(ipa, i); call 0 returned 100% 774: 587: POINT4D p2_4d = getPoint4d(ipa, i+1); call 0 returned 100% -: 588: 774: 589: double segment_fraction = (length_fraction - length_fraction_consumed) / segment_length_frac; 774: 590: interpolate_point4d(&p1_4d, &p2_4d, &pt, segment_fraction); call 0 returned 100% 774: 591: ptarray_set_point4d(opa, points_found++, &pt); call 0 returned 100% 774: 592: length_fraction += length_fraction_increment; -: 593: } -: 594: 1052: 595: length_fraction_consumed += segment_length_frac; -: 596: 1052: 597: p1 = p2; -: 598: } -: 599: -: 600: /* Return the last point on the line. This shouldn't happen, but -: 601: * could if there's some floating point rounding errors. */ 770: 602: if (points_found < points_to_interpolate) { branch 0 taken 0% (fallthrough) branch 1 taken 100% #####: 603: getPoint4d_p(ipa, ipa->npoints - 1, &pt); call 0 never executed #####: 604: ptarray_set_point4d(opa, points_found, &pt); call 0 never executed -: 605: } -: 606: 770: 607: return opa; -: 608:} -: 609: -: 610:extern LWPOINT * function lwline_interpolate_point_3d called 4 returned 100% blocks executed 74% 4: 611:lwline_interpolate_point_3d(const LWLINE *line, double distance) -: 612:{ -: 613: double length, slength, tlength; -: 614: POINTARRAY *ipa; -: 615: POINT4D pt; -: 616: int nsegs, i; 4: 617: LWGEOM *geom = lwline_as_lwgeom(line); call 0 returned 100% 4: 618: int has_z = lwgeom_has_z(geom); call 0 returned 100% 4: 619: int has_m = lwgeom_has_m(geom); call 0 returned 100% 4: 620: ipa = line->points; -: 621: 4: 622: printf("titi\n"); call 0 returned 100% -: 623: -: 624: /* Empty.InterpolatePoint == Point Empty */ 4: 625: if (lwline_is_empty(line)) call 0 returned 100% branch 1 taken 0% (fallthrough) branch 2 taken 100% -: 626: { #####: 627: printf("test0\n"); call 0 never executed #####: 628: return lwpoint_construct_empty(line->srid, has_z, has_m); call 0 never executed -: 629: } -: 630: -: 631: /* If distance is one of the two extremes, return the point on that -: 632: * end rather than doing any expensive computations -: 633: */ 4: 634: if (distance == 0.0 || distance == 1.0) branch 0 taken 50% (fallthrough) branch 1 taken 50% branch 2 taken 0% (fallthrough) branch 3 taken 100% -: 635: { 2: 636: if (distance == 0.0) branch 0 taken 100% (fallthrough) branch 1 taken 0% -: 637: { 2: 638: getPoint4d_p(ipa, 0, &pt); call 0 returned 100% 2: 639: printf("test1\n"); call 0 returned 100% -: 640: -: 641: } -: 642: else -: 643: { #####: 644: getPoint4d_p(ipa, ipa->npoints - 1, &pt); call 0 never executed #####: 645: printf("test2\n"); call 0 never executed -: 646: } -: 647: -: 648: 2: 649: return lwpoint_make(line->srid, has_z, has_m, &pt); call 0 returned 100% -: 650: } -: 651: -: 652: /* Interpolate a point on the line */ 2: 653: nsegs = ipa->npoints - 1; 2: 654: length = ptarray_length(ipa); call 0 returned 100% 2: 655: tlength = 0; 2*: 656: for (i = 0; i < nsegs; i++) branch 0 taken 100% branch 1 taken 0% (fallthrough) -: 657: { -: 658: POINT4D p1, p2; 2: 659: POINT4D *p1ptr = &p1, *p2ptr = &p2; /* don't break -: 660: * strict-aliasing rules -: 661: */ -: 662: 2: 663: getPoint4d_p(ipa, i, &p1); call 0 returned 100% 2: 664: getPoint4d_p(ipa, i + 1, &p2); call 0 returned 100% -: 665: -: 666: /* Find the relative length of this segment */ 2: 667: slength = distance3d_pt_pt((POINT3D *)p1ptr, (POINT3D *)p2ptr) / length; call 0 returned 100% -: 668: -: 669: /* If our target distance is before the total length we've seen -: 670: * so far. create a new point some distance down the current -: 671: * segment. -: 672: */ 2: 673: if (distance < tlength + slength) branch 0 taken 100% (fallthrough) branch 1 taken 0% -: 674: { 2: 675: double dseg = (distance - tlength) / slength; 2: 676: interpolate_point4d(&p1, &p2, &pt, dseg); call 0 returned 100% 2: 677: return lwpoint_make(line->srid, has_z, has_m, &pt); call 0 returned 100% -: 678: } #####: 679: printf("test4\n"); call 0 never executed #####: 680: tlength += slength; -: 681: } -: 682: -: 683: /* Return the last point on the line. This shouldn't happen, but -: 684: * could if there's some floating point rounding errors. */ #####: 685: getPoint4d_p(ipa, ipa->npoints - 1, &pt); call 0 never executed #####: 686: return lwpoint_make(line->srid, has_z, has_m, &pt); call 0 never executed -: 687:}