docs: static Geometry construct(MultiVertexGeometry mvg) {
  		if (mvg.isEmpty())
  			return new Polygon(mvg.getDescription());
  
  		MultiVertexGeometryImpl mvg_impl = (MultiVertexGeometryImpl) mvg._getImpl();
  		int N = mvg_impl.getPointCount();
  
  		if (N <= 2) {
  			if (N == 1 || mvg_impl.getXY(0).equals(mvg_impl.getXY(1))) {
  				Point point = new Point(mvg_impl.getDescription());
  				mvg_impl.getPointByVal(0, point);
  				return point;
  			} else {
  				Point pt = new Point();
  				Polyline polyline = new Polyline(mvg_impl.getDescription());
  				mvg_impl.getPointByVal(0, pt);
  				polyline.startPath(pt);
  				mvg_impl.getPointByVal(1, pt);
  				polyline.lineTo(pt);
  				return polyline;
  			}
  		}
  
  		AttributeStreamOfDbl stream = (AttributeStreamOfDbl) mvg_impl.getAttributeStreamRef(VertexDescription.Semantics.POSITION);
  		ConvexHull convex_hull = new ConvexHull(stream, N);
  
  		int t0 = 0, tm = 1;
  		Point2D pt_0 = new Point2D();
  		Point2D pt_m = new Point2D();
  		Point2D pt_p = new Point2D();
  
  		stream.read(t0 << 1, pt_0);
  
  		while (true) {
  			if (tm >= N)
  				break;
  
  			stream.read(tm << 1, pt_m);
  			if (!pt_m.isEqual(pt_0, NumberUtils.doubleEps()))
  				break;
  
  			tm++; // We don't want to close the gap between t0 and tm.
  		}
  
  		convex_hull.m_tree_hull.addElement(t0, -1);
  
  		if (tm < N) {
  			convex_hull.m_tree_hull.addBiggestElement(tm, -1);
  
  			for (int tp = tm + 1; tp < mvg_impl.getPointCount(); tp++) {// Dynamically insert into the current convex hull
  
  				stream.read(tp << 1, pt_p);
  				int p = convex_hull.treeHull_(pt_p);
  
  				if (p != -1)
  					convex_hull.m_tree_hull.setElement(p, tp); // reset the place holder to the point index.
  			}
  		}
  
  		// Extracts the convex hull from the tree. Reading the tree in order from first to last is the resulting convex hull.
  
  		VertexDescription description = mvg_impl.getDescription();
  		boolean b_has_attributes = (description.getAttributeCount() > 1);
  		int point_count = convex_hull.m_tree_hull.size(-1);
  
  		Geometry hull;
  
  		if (point_count >= 2) {
  			if (point_count >= 3)
  				hull = new Polygon(description);
  			else
  				hull = new Polyline(description);
  
  			MultiPathImpl hull_impl = (MultiPathImpl) hull._getImpl();
  			hull_impl.addPath((Point2D[]) null, 0, true);
  
  			Point point = null;
  			if (b_has_attributes)
  				point = new Point();
  
  			for (int i = convex_hull.m_tree_hull.getFirst(-1); i != -1; i = convex_hull.m_tree_hull.getNext(i)) {
  				if (b_has_attributes) {
  					mvg_impl.getPointByVal(convex_hull.m_tree_hull.getElement(i), point);
  					hull_impl.insertPoint(0, -1, point);
  				} else {
  					stream.read(convex_hull.m_tree_hull.getElement(i) << 1, pt_p);
  					hull_impl.insertPoint(0, -1, pt_p);
  				}
  			}
  		} else {
  			assert (point_count == 1);
  
  			if (b_has_attributes) {
  				Point point = new Point(description);
  				mvg_impl.getPointByVal(convex_hull.m_tree_hull.getElement(convex_hull.m_tree_hull.getFirst(-1)), point);
  				hull = point;
  			} else {
  				stream.read(convex_hull.m_tree_hull.getElement(convex_hull.m_tree_hull.getFirst(-1)) << 1, pt_p);
  				hull = new Point(pt_p);
  			}
  		}
  
  		return hull;
  	}