HighMap library (C++)
Loading...
Searching...
No Matches
path.hpp
Go to the documentation of this file.
1/* Copyright (c) 2023 Otto Link. Distributed under the terms of the GNU General
2 Public License. The full license is in the file LICENSE, distributed with
3 this software. */
4
17#pragma once
18#include "highmap/boundary.hpp"
21
22namespace hmap
23{
24
42class Path : public Cloud
43{
44public:
45 enum class EdgeDivisionMode : int
46 {
49 };
50
51 // ==========================================================================
52 // Constructors
53 // ==========================================================================
54
59 Path() = default;
60
69 Path(int npoints, std::uint32_t seed, glm::vec4 bbox = {0.f, 1.f, 0.f, 1.f})
70 : Cloud(npoints, seed, bbox){};
71
77 Path(std::vector<Point> points) : Cloud(points){};
78
86 Path(std::vector<float> x, std::vector<float> y) : Cloud(x, y){};
87
96 Path(std::vector<float> x, std::vector<float> y, std::vector<float> v)
97 : Cloud(x, y, v){};
98
110 Path(const std::vector<glm::ivec2> &indices,
111 const glm::ivec2 &shape,
112 const glm::vec4 &bbox = {0.f, 1.f, 0.f, 1.f})
113 : Cloud(indices, shape, bbox){};
114
118 Path(const std::vector<glm::vec3> &xyv) : Cloud(xyv){};
119
120 // ==========================================================================
121 // Accessors
122 // ==========================================================================
123
135 std::vector<float> get_arc_length() const;
136
148 std::vector<float> get_cumulative_distance() const;
149
156 std::vector<float> get_curvature(bool normalized = false) const;
157
165 std::vector<Point> get_edge_centers() const;
166
171 std::vector<glm::vec2> get_normals() const;
172
177 std::vector<glm::vec2> get_tangents() const;
178
189 std::vector<float> get_values() const;
190
200 std::vector<float> get_x() const;
201
213 std::vector<float> get_xy() const;
214
224 std::vector<float> get_y() const;
225
230 bool is_closed() const;
231
236 void set_closed(bool new_value);
237
238 // ==========================================================================
239 // Basic Ops
240 // ==========================================================================
241
248 void clear();
249
263 void enforce_monotonic_values(bool decreasing = true);
264
276 void reorder_nns(int start_index = 0);
277
285 void reverse();
286
287 // ==========================================================================
288 // Sampling
289 // ==========================================================================
290
299 void divide();
300
313 float delta,
315
331 void resample_interp(
332 int npoints,
334
345 void resample_uniform(
347
361 glm::vec3 sample_at(float t,
362 const std::vector<float> *p_arc = nullptr,
363 glm::vec2 *p_tangent = nullptr) const;
364
375 void subsample(int step);
376
377 // ==========================================================================
378 // Conversion / IO
379 // ==========================================================================
380
396 void to_array(Array &array,
397 glm::vec4 bbox = {0.f, 1.f, 0.f, 1.f},
398 bool filled = false) const;
399
401 Array to_array(glm::ivec2 shape,
402 glm::vec4 bbox = {0.f, 1.f, 0.f, 1.f},
403 bool filled = false) const;
404
406 void to_array_mask(Array &array,
407 glm::vec4 bbox = {0.f, 1.f, 0.f, 1.f},
408 bool filled = false) const;
409
424 void to_png(std::string fname, glm::ivec2 shape = {512, 512});
425
426private:
427 enum class PathClosure : int
428 {
429 PT_OPEN,
430 PT_CLOSE,
431 } path_closure = PathClosure::PT_OPEN;
432};
433
434// ==========================================================================
435// Functions
436// ==========================================================================
437
462Path bezier(const Path &path,
463 float curvature_ratio = 0.3f,
464 int edge_divisions = 10,
466
489Path bezier_round(
490 const Path &path,
491 float curvature_ratio = 0.3f,
492 int edge_divisions = 10,
494
521Path bspline(const Path &path,
522 int edge_divisions = 10,
524
545Path catmullrom(
546 const Path &path,
547 int edge_divisions = 10,
549
576Path decasteljau(
577 const Path &path,
578 int edge_divisions = 10,
580
603Path decimate_vw(const Path &path, int n_points_target = 3);
604
640Path fractalize(const Path &path,
641 int iterations,
642 std::uint32_t seed,
643 float sigma = 0.2f,
644 int orientation = 0,
645 float persistence = 1.f,
646 Array *p_control_field = nullptr,
647 glm::vec4 bbox = {0.f, 1.f, 0.f, 1.f},
648 bool bounded = false);
649
668Path inflate(const Path &path, float strength, bool resample = true);
669
698Path meanderize(
699 const Path &path,
700 float ratio,
701 float noise_ratio = 0.1f,
702 std::uint32_t seed = 1,
703 int iterations = 1,
704 int edge_divisions = 10,
706
720Array path_sdf_to_array(const Path &path,
721 glm::ivec2 shape,
722 glm::vec4 bbox_array = {0.f, 1.f, 0.f, 1.f},
723 const Array *p_noise_x = nullptr,
724 const Array *p_noise_y = nullptr);
725
742Path remove_geometric_loops(const Path &path);
743
764Path scale(const Path &path, glm::vec2 scale, glm::vec2 center = {0.5f, 0.5f});
765
766Path scale(const Path &path, float scale, glm::vec2 center = {0.5f, 0.5f});
767
803Path smooth(const Path &path,
804 int navg = 1,
805 float averaging_intensity = 1.f,
806 float inertia = 0.f);
807
841Path squiggle(const Path &path,
842 int iterations = 4,
843 std::uint32_t seed = 0,
844 float height_ratio = 0.5f,
845 int orientation = 0,
846 const Array *p_weights = nullptr,
847 const Array *p_mask = nullptr,
848 glm::vec4 bbox = {0.f, 1.f, 0.f, 1.f});
849
870std::vector<Path> squiggle_branches(const Path &path,
871 int iterations = 4,
872 std::uint32_t seed = 0,
873 float branch_probability = 0.3f,
874 int max_branches = 8,
875 float height_ratio = 0.5f,
876 int orientation = 0,
877 const Array *p_weights = nullptr,
878 const Array *p_mask = nullptr,
879 glm::vec4 bbox = {0.f, 1.f, 0.f, 1.f});
880
881// ==========================================================================
882// Verification Functions
883// ==========================================================================
884
896bool assert_start_end_points(const Path &path1,
897 const Path &path2,
898 float tol = 1e-6f,
899 bool verbose = false);
900
907float chamfer_distance(const Path &a, const Path &b);
908
918bool has_duplicates(const Path &path, float tol = 1e-6f);
919
920} // namespace hmap
Header file for boundary condition functions and utilities.
Array class, helper to manipulate 2D float array with "(i, j)" indexing.
Definition array.hpp:32
Represents a collection of unordered points in 2D space.
Definition cloud.hpp:50
std::vector< Point > points
Points of the cloud.
Definition cloud.hpp:52
Represents an ordered set of points in 2D, forming a polyline (open or closed).
Definition path.hpp:43
Path(const std::vector< glm::ivec2 > &indices, const glm::ivec2 &shape, const glm::vec4 &bbox={0.f, 1.f, 0.f, 1.f})
Construct a point cloud from grid indices mapped to a bounding box.
Definition path.hpp:110
Path(std::vector< float > x, std::vector< float > y)
Construct a new Path object based on x and y coordinates. Initializes a path with the specified x and...
Definition path.hpp:86
std::vector< float > get_arc_length() const
Get the arc length of the path.
Definition path.cpp:78
std::vector< Point > get_edge_centers() const
Compute midpoints of path edges.
Definition path.cpp:130
std::vector< float > get_xy() const
Get the coordinates of the points as a single vector.
Definition path.cpp:198
void to_array_mask(Array &array, glm::vec4 bbox={0.f, 1.f, 0.f, 1.f}, bool filled=false) const
See hmap::to_array.
Definition path.cpp:472
Path()=default
Construct a new Path object with default properties. Initializes an empty path with the closed proper...
Path(int npoints, std::uint32_t seed, glm::vec4 bbox={0.f, 1.f, 0.f, 1.f})
Construct a new Path object with random positions and values. Initializes a path with a specified num...
Definition path.hpp:69
bool is_closed() const
Check whether the path is closed.
Definition path.cpp:225
Path(std::vector< float > x, std::vector< float > y, std::vector< float > v)
Construct a new Path object based on x, y coordinates, and values. Initializes a path with the specif...
Definition path.hpp:96
void enforce_monotonic_values(bool decreasing=true)
Enforces monotonicity on the values of the points in the path.
Definition path.cpp:58
void to_array(Array &array, glm::vec4 bbox={0.f, 1.f, 0.f, 1.f}, bool filled=false) const
Project path points to an array.
Definition path.cpp:413
EdgeDivisionMode
Definition path.hpp:46
std::vector< float > get_values() const
Get the values assigned to the points on the path.
Definition path.cpp:178
void resample_by_spacing(float delta, InterpolationMethod1D itp_method=InterpolationMethod1D::LINEAR)
Resample the path to achieve an approximately constant distance between points.
Definition path.cpp:276
void resample_uniform(InterpolationMethod1D itp_method=InterpolationMethod1D::LINEAR)
Resample the path to achieve fairly uniform distance between consecutive points.
Definition path.cpp:325
void divide()
Divide the path by adding a point between each pair of consecutive points.
Definition path.cpp:33
void subsample(int step)
Subsample the path by keeping only every n-th point.
Definition path.cpp:397
std::vector< float > get_cumulative_distance() const
Get the cumulative distance of the path.
Definition path.cpp:87
void to_png(std::string fname, glm::ivec2 shape={512, 512})
Export path as PNG image file.
Definition path.cpp:481
std::vector< float > get_curvature(bool normalized=false) const
Computes the signed curvature at each point of the path.
Definition path.cpp:104
void reverse()
Reverse the order of points in the path.
Definition path.cpp:351
std::vector< float > get_y() const
Get the y coordinates of the points on the path.
Definition path.cpp:215
glm::vec3 sample_at(float t, const std::vector< float > *p_arc=nullptr, glm::vec2 *p_tangent=nullptr) const
Sample the path using normalized arc-length parameterization.
Definition path.cpp:356
std::vector< float > get_x() const
Get the x coordinates of the points on the path.
Definition path.cpp:188
std::vector< glm::vec2 > get_normals() const
Computes unit normals at each point of the path.
Definition path.cpp:150
void reorder_nns(int start_index=0)
Reorder points using a nearest neighbor search.
Definition path.cpp:230
void clear()
Clear the path data.
Definition path.cpp:28
std::vector< glm::vec2 > get_tangents() const
Computes unit tangents at each point of the path.
Definition path.cpp:160
void set_closed(bool new_value)
Set whether the path is closed.
Definition path.cpp:392
Path(const std::vector< glm::vec3 > &xyv)
Constructs a new Path object from lists of xyz data as glm::vec3.
Definition path.hpp:118
Path(std::vector< Point > points)
Construct a new Path object based on a list of points. Initializes a path with the specified points a...
Definition path.hpp:77
void resample_interp(int npoints, InterpolationMethod1D itp_method=InterpolationMethod1D::CUBIC)
Resamples the path using cubic interpolation along arc length.
Definition path.cpp:286
Definition of the Cloud class for manipulating sets of 2D points.
Defines a 1D interpolation class using the GSL (GNU Scientific Library).
Definition algebra.hpp:23
Path squiggle(const Path &path, int iterations=4, std::uint32_t seed=0, float height_ratio=0.5f, int orientation=0, const Array *p_weights=nullptr, const Array *p_mask=nullptr, glm::vec4 bbox={0.f, 1.f, 0.f, 1.f})
Generates a continuous, non-self-intersecting squiggle curve by applying the squiggle recursive trian...
Definition path_squiggle.cpp:169
bool has_duplicates(const Cloud &cloud, float eps=1e-9f, bool xy_only=true)
Checks whether the point cloud contains duplicate points.
Definition cloud_functions.cpp:72
Path bspline(const Path &path, int edge_divisions=10, Path::EdgeDivisionMode edm=Path::EdgeDivisionMode::EDM_PER_EDGE)
Smooth the path using B-Spline curves.
Definition path_functions.cpp:159
Array path_sdf_to_array(const Path &path, glm::ivec2 shape, glm::vec4 bbox_array={0.f, 1.f, 0.f, 1.f}, const Array *p_noise_x=nullptr, const Array *p_noise_y=nullptr)
Compute a distance field from a point path.
Definition path_functions.cpp:457
Path bezier_round(const Path &path, float curvature_ratio=0.3f, int edge_divisions=10, Path::EdgeDivisionMode edm=Path::EdgeDivisionMode::EDM_PER_EDGE)
Smooth the path using Bezier curves (alternative method).
Definition path_functions.cpp:101
Array normalized(const Array &array, NormalizationMethod method)
Returns a normalized copy of an array.
Definition normalize.cpp:51
InterpolationMethod1D
Enumeration of the available 1D interpolation methods.
Definition interpolate1d.hpp:36
@ CUBIC
Cubic spline interpolation.
Definition interpolate1d.hpp:39
@ LINEAR
Linear interpolation.
Definition interpolate1d.hpp:41
Path meanderize(const Path &path, float ratio, float noise_ratio=0.1f, std::uint32_t seed=1, int iterations=1, int edge_divisions=10, Path::EdgeDivisionMode edm=Path::EdgeDivisionMode::EDM_PER_EDGE)
Add "meanders" to the path.
Definition path_functions.cpp:388
Path fractalize(const Path &path, int iterations, std::uint32_t seed, float sigma=0.2f, int orientation=0, float persistence=1.f, Array *p_control_field=nullptr, glm::vec4 bbox={0.f, 1.f, 0.f, 1.f}, bool bounded=false)
Applies fractalization to the path by adding points and randomly displacing their positions.
Definition path_functions.cpp:256
bool assert_start_end_points(const Path &path1, const Path &path2, float tol=1e-6f, bool verbose=false)
Asserts that the start and end points of two paths are within a specified tolerance.
Definition path_verification.cpp:17
Path remove_geometric_loops(const Path &path)
Removes geometric loops in a 2D path caused by self-intersections.
Definition path_functions.cpp:512
std::vector< Path > squiggle_branches(const Path &path, int iterations=4, std::uint32_t seed=0, float branch_probability=0.3f, int max_branches=8, float height_ratio=0.5f, int orientation=0, const Array *p_weights=nullptr, const Array *p_mask=nullptr, glm::vec4 bbox={0.f, 1.f, 0.f, 1.f})
Generates squiggle paths with secondary tributary branches along each edge.
Definition path_squiggle.cpp:283
Path inflate(const Path &path, float strength, bool resample=true)
Inflate (offset) a path along its normals using curvature.
Definition path_functions.cpp:358
Cloud scale(const Cloud &cloud, glm::vec2 scale, glm::vec2 center={0.5f, 0.5f})
Scales the point coordinates in a cloud relative to a center point.
Definition cloud_functions.cpp:165
Path decimate_vw(const Path &path, int n_points_target=3)
Simplifies the current path using the Visvalingam-Whyatt algorithm.
Definition path_functions.cpp:223
Path catmullrom(const Path &path, int edge_divisions=10, Path::EdgeDivisionMode edm=Path::EdgeDivisionMode::EDM_PER_EDGE)
Smooth the path using Catmull-Rom curves.
Definition path_functions.cpp:179
float chamfer_distance(const Path &a, const Path &b)
Calculate the chamfer distance between two paths.
Definition path_verification.cpp:43
Path bezier(const Path &path, float curvature_ratio=0.3f, int edge_divisions=10, Path::EdgeDivisionMode edm=Path::EdgeDivisionMode::EDM_PER_EDGE)
Smooth the path using Bezier curves.
Definition path_functions.cpp:45
Path smooth(const Path &path, int navg=1, float averaging_intensity=1.f, float inertia=0.f)
Applies a smoothing operation to the path points using a moving average filter.
Definition path_functions.cpp:564
Path decasteljau(const Path &path, int edge_divisions=10, Path::EdgeDivisionMode edm=Path::EdgeDivisionMode::EDM_PER_EDGE)
Smooth the path using De Casteljau curves.
Definition path_functions.cpp:201
Array step(glm::ivec2 shape, float angle, float slope, const Array *p_ctrl_param=nullptr, const Array *p_noise_x=nullptr, const Array *p_noise_y=nullptr, glm::vec2 center={0.5f, 0.5f}, glm::vec4 bbox={0.f, 1.f, 0.f, 1.f})
Return a step function (Heaviside with an optional talus slope at the transition).
Definition primitives.cpp:395