module.exports = LineString; var util = require('util'); var Geometry = require('./geometry'); var Types = require('./types'); var Point = require('./point'); var BinaryWriter = require('./binarywriter'); function LineString(points, srid) { Geometry.call(this); this.points = points || []; this.srid = srid; if (this.points.length > 0) { this.hasZ = this.points[0].hasZ; this.hasM = this.points[0].hasM; } } util.inherits(LineString, Geometry); LineString.Z = function (points, srid) { var lineString = new LineString(points, srid); lineString.hasZ = true; return lineString; }; LineString.M = function (points, srid) { var lineString = new LineString(points, srid); lineString.hasM = true; return lineString; }; LineString.ZM = function (points, srid) { var lineString = new LineString(points, srid); lineString.hasZ = true; lineString.hasM = true; return lineString; }; LineString._parseWkt = function (value, options) { var lineString = new LineString(); lineString.srid = options.srid; lineString.hasZ = options.hasZ; lineString.hasM = options.hasM; if (value.isMatch(['EMPTY'])) return lineString; value.expectGroupStart(); lineString.points.push.apply(lineString.points, value.matchCoordinates(options)); value.expectGroupEnd(); return lineString; }; LineString._parseWkb = function (value, options) { var lineString = new LineString(); lineString.srid = options.srid; lineString.hasZ = options.hasZ; lineString.hasM = options.hasM; var pointCount = value.readUInt32(); for (var i = 0; i < pointCount; i++) lineString.points.push(Point._readWkbPoint(value, options)); return lineString; }; LineString._parseTwkb = function (value, options) { var lineString = new LineString(); lineString.hasZ = options.hasZ; lineString.hasM = options.hasM; if (options.isEmpty) return lineString; var previousPoint = new Point(0, 0, options.hasZ ? 0 : undefined, options.hasM ? 0 : undefined); var pointCount = value.readVarInt(); for (var i = 0; i < pointCount; i++) lineString.points.push(Point._readTwkbPoint(value, options, previousPoint)); return lineString; }; LineString._parseGeoJSON = function (value) { var lineString = new LineString(); if (value.coordinates.length > 0) lineString.hasZ = value.coordinates[0].length > 2; for (var i = 0; i < value.coordinates.length; i++) lineString.points.push(Point._readGeoJSONPoint(value.coordinates[i])); return lineString; }; LineString.prototype.toWkt = function () { if (this.points.length === 0) return this._getWktType(Types.wkt.LineString, true); return this._getWktType(Types.wkt.LineString, false) + this._toInnerWkt(); }; LineString.prototype._toInnerWkt = function () { var innerWkt = '('; for (var i = 0; i < this.points.length; i++) innerWkt += this._getWktCoordinate(this.points[i]) + ','; innerWkt = innerWkt.slice(0, -1); innerWkt += ')'; return innerWkt; }; LineString.prototype.toWkb = function (parentOptions) { var wkb = new BinaryWriter(this._getWkbSize()); wkb.writeInt8(1); this._writeWkbType(wkb, Types.wkb.LineString, parentOptions); wkb.writeUInt32LE(this.points.length); for (var i = 0; i < this.points.length; i++) this.points[i]._writeWkbPoint(wkb); return wkb.buffer; }; LineString.prototype.toTwkb = function () { var twkb = new BinaryWriter(0, true); var precision = Geometry.getTwkbPrecision(5, 0, 0); var isEmpty = this.points.length === 0; this._writeTwkbHeader(twkb, Types.wkb.LineString, precision, isEmpty); if (this.points.length > 0) { twkb.writeVarInt(this.points.length); var previousPoint = new Point(0, 0, 0, 0); for (var i = 0; i < this.points.length; i++) this.points[i]._writeTwkbPoint(twkb, precision, previousPoint); } return twkb.buffer; }; LineString.prototype._getWkbSize = function () { var coordinateSize = 16; if (this.hasZ) coordinateSize += 8; if (this.hasM) coordinateSize += 8; return 1 + 4 + 4 + (this.points.length * coordinateSize); }; LineString.prototype.toGeoJSON = function (options) { var geoJSON = Geometry.prototype.toGeoJSON.call(this, options); geoJSON.type = Types.geoJSON.LineString; geoJSON.coordinates = []; for (var i = 0; i < this.points.length; i++) { if (this.hasZ) geoJSON.coordinates.push([this.points[i].x, this.points[i].y, this.points[i].z]); else geoJSON.coordinates.push([this.points[i].x, this.points[i].y]); } return geoJSON; };