1 /**
2 Describes a Bézier curve in 3D space.
3 
4 Copyright:
5 Copyright (c) 2007-2018 Juan Linietsky, Ariel Manzur.  
6 Copyright (c) 2014-2018 Godot Engine contributors (cf. AUTHORS.md)  
7 Copyright (c) 2017-2018 Godot-D contributors  
8 
9 License: $(LINK2 https://opensource.org/licenses/MIT, MIT License)
10 
11 
12 */
13 module godot.curve3d;
14 import std.meta : AliasSeq, staticIndexOf;
15 import std.traits : Unqual;
16 import godot.d.traits;
17 import godot.core;
18 import godot.c;
19 import godot.d.bind;
20 import godot.d.reference;
21 import godot.globalenums;
22 import godot.object;
23 import godot.classdb;
24 import godot.resource;
25 /**
26 Describes a Bézier curve in 3D space.
27 
28 This class describes a Bézier curve in 3D space. It is mainly used to give a shape to a $(D Path), but can be manually sampled for other purposes.
29 It keeps a cache of precalculated points along the curve, to speed up further calculations.
30 */
31 @GodotBaseClass struct Curve3D
32 {
33 	package(godot) enum string _GODOT_internal_name = "Curve3D";
34 public:
35 @nogc nothrow:
36 	union { /** */ godot_object _godot_object; /** */ Resource _GODOT_base; }
37 	alias _GODOT_base this;
38 	alias BaseClasses = AliasSeq!(typeof(_GODOT_base), typeof(_GODOT_base).BaseClasses);
39 	package(godot) __gshared bool _classBindingInitialized = false;
40 	package(godot) static struct GDNativeClassBinding
41 	{
42 		__gshared:
43 		@GodotName("_get_data") GodotMethod!(Dictionary) _getData;
44 		@GodotName("_set_data") GodotMethod!(void, Dictionary) _setData;
45 		@GodotName("add_point") GodotMethod!(void, Vector3, Vector3, Vector3, long) addPoint;
46 		@GodotName("clear_points") GodotMethod!(void) clearPoints;
47 		@GodotName("get_bake_interval") GodotMethod!(double) getBakeInterval;
48 		@GodotName("get_baked_length") GodotMethod!(double) getBakedLength;
49 		@GodotName("get_baked_points") GodotMethod!(PoolVector3Array) getBakedPoints;
50 		@GodotName("get_baked_tilts") GodotMethod!(PoolRealArray) getBakedTilts;
51 		@GodotName("get_baked_up_vectors") GodotMethod!(PoolVector3Array) getBakedUpVectors;
52 		@GodotName("get_closest_offset") GodotMethod!(double, Vector3) getClosestOffset;
53 		@GodotName("get_closest_point") GodotMethod!(Vector3, Vector3) getClosestPoint;
54 		@GodotName("get_point_count") GodotMethod!(long) getPointCount;
55 		@GodotName("get_point_in") GodotMethod!(Vector3, long) getPointIn;
56 		@GodotName("get_point_out") GodotMethod!(Vector3, long) getPointOut;
57 		@GodotName("get_point_position") GodotMethod!(Vector3, long) getPointPosition;
58 		@GodotName("get_point_tilt") GodotMethod!(double, long) getPointTilt;
59 		@GodotName("interpolate") GodotMethod!(Vector3, long, double) interpolate;
60 		@GodotName("interpolate_baked") GodotMethod!(Vector3, double, bool) interpolateBaked;
61 		@GodotName("interpolate_baked_up_vector") GodotMethod!(Vector3, double, bool) interpolateBakedUpVector;
62 		@GodotName("interpolatef") GodotMethod!(Vector3, double) interpolatef;
63 		@GodotName("is_up_vector_enabled") GodotMethod!(bool) isUpVectorEnabled;
64 		@GodotName("remove_point") GodotMethod!(void, long) removePoint;
65 		@GodotName("set_bake_interval") GodotMethod!(void, double) setBakeInterval;
66 		@GodotName("set_point_in") GodotMethod!(void, long, Vector3) setPointIn;
67 		@GodotName("set_point_out") GodotMethod!(void, long, Vector3) setPointOut;
68 		@GodotName("set_point_position") GodotMethod!(void, long, Vector3) setPointPosition;
69 		@GodotName("set_point_tilt") GodotMethod!(void, long, double) setPointTilt;
70 		@GodotName("set_up_vector_enabled") GodotMethod!(void, bool) setUpVectorEnabled;
71 		@GodotName("tessellate") GodotMethod!(PoolVector3Array, long, double) tessellate;
72 	}
73 	/// 
74 	pragma(inline, true) bool opEquals(in Curve3D other) const
75 	{ return _godot_object.ptr is other._godot_object.ptr; }
76 	/// 
77 	pragma(inline, true) typeof(null) opAssign(typeof(null) n)
78 	{ _godot_object.ptr = n; return null; }
79 	/// 
80 	pragma(inline, true) bool opEquals(typeof(null) n) const
81 	{ return _godot_object.ptr is n; }
82 	/// 
83 	size_t toHash() const @trusted { return cast(size_t)_godot_object.ptr; }
84 	mixin baseCasts;
85 	/// Construct a new instance of Curve3D.
86 	/// Note: use `memnew!Curve3D` instead.
87 	static Curve3D _new()
88 	{
89 		static godot_class_constructor constructor;
90 		if(constructor is null) constructor = _godot_api.godot_get_class_constructor("Curve3D");
91 		if(constructor is null) return typeof(this).init;
92 		return cast(Curve3D)(constructor());
93 	}
94 	@disable new(size_t s);
95 	/**
96 	
97 	*/
98 	Dictionary _getData() const
99 	{
100 		Array _GODOT_args = Array.make();
101 		String _GODOT_method_name = String("_get_data");
102 		return this.callv(_GODOT_method_name, _GODOT_args).as!(RefOrT!Dictionary);
103 	}
104 	/**
105 	
106 	*/
107 	void _setData(in Dictionary arg0)
108 	{
109 		Array _GODOT_args = Array.make();
110 		_GODOT_args.append(arg0);
111 		String _GODOT_method_name = String("_set_data");
112 		this.callv(_GODOT_method_name, _GODOT_args);
113 	}
114 	/**
115 	Adds a point to a curve at `position`, with control points `in` and `out`.
116 	If `at_position` is given, the point is inserted before the point number `at_position`, moving that point (and every point after) after the inserted point. If `at_position` is not given, or is an illegal value (`at_position <0` or `at_position >= $(D getPointCount)`), the point will be appended at the end of the point list.
117 	*/
118 	void addPoint(in Vector3 position, in Vector3 _in = Vector3(0, 0, 0), in Vector3 _out = Vector3(0, 0, 0), in long at_position = -1)
119 	{
120 		checkClassBinding!(typeof(this))();
121 		ptrcall!(void)(GDNativeClassBinding.addPoint, _godot_object, position, _in, _out, at_position);
122 	}
123 	/**
124 	Removes all points from the curve.
125 	*/
126 	void clearPoints()
127 	{
128 		checkClassBinding!(typeof(this))();
129 		ptrcall!(void)(GDNativeClassBinding.clearPoints, _godot_object);
130 	}
131 	/**
132 	
133 	*/
134 	double getBakeInterval() const
135 	{
136 		checkClassBinding!(typeof(this))();
137 		return ptrcall!(double)(GDNativeClassBinding.getBakeInterval, _godot_object);
138 	}
139 	/**
140 	Returns the total length of the curve, based on the cached points. Given enough density (see $(D bakeInterval)), it should be approximate enough.
141 	*/
142 	double getBakedLength() const
143 	{
144 		checkClassBinding!(typeof(this))();
145 		return ptrcall!(double)(GDNativeClassBinding.getBakedLength, _godot_object);
146 	}
147 	/**
148 	Returns the cache of points as a $(D PoolVector3Array).
149 	*/
150 	PoolVector3Array getBakedPoints() const
151 	{
152 		checkClassBinding!(typeof(this))();
153 		return ptrcall!(PoolVector3Array)(GDNativeClassBinding.getBakedPoints, _godot_object);
154 	}
155 	/**
156 	Returns the cache of tilts as a $(D PoolRealArray).
157 	*/
158 	PoolRealArray getBakedTilts() const
159 	{
160 		checkClassBinding!(typeof(this))();
161 		return ptrcall!(PoolRealArray)(GDNativeClassBinding.getBakedTilts, _godot_object);
162 	}
163 	/**
164 	Returns the cache of up vectors as a $(D PoolVector3Array).
165 	If $(D upVectorEnabled) is `false`, the cache will be empty.
166 	*/
167 	PoolVector3Array getBakedUpVectors() const
168 	{
169 		checkClassBinding!(typeof(this))();
170 		return ptrcall!(PoolVector3Array)(GDNativeClassBinding.getBakedUpVectors, _godot_object);
171 	}
172 	/**
173 	Returns the closest offset to `to_point`. This offset is meant to be used in $(D interpolateBaked) or $(D interpolateBakedUpVector).
174 	`to_point` must be in this curve's local space.
175 	*/
176 	double getClosestOffset(in Vector3 to_point) const
177 	{
178 		checkClassBinding!(typeof(this))();
179 		return ptrcall!(double)(GDNativeClassBinding.getClosestOffset, _godot_object, to_point);
180 	}
181 	/**
182 	Returns the closest baked point (in curve's local space) to `to_point`.
183 	`to_point` must be in this curve's local space.
184 	*/
185 	Vector3 getClosestPoint(in Vector3 to_point) const
186 	{
187 		checkClassBinding!(typeof(this))();
188 		return ptrcall!(Vector3)(GDNativeClassBinding.getClosestPoint, _godot_object, to_point);
189 	}
190 	/**
191 	Returns the number of points describing the curve.
192 	*/
193 	long getPointCount() const
194 	{
195 		checkClassBinding!(typeof(this))();
196 		return ptrcall!(long)(GDNativeClassBinding.getPointCount, _godot_object);
197 	}
198 	/**
199 	Returns the position of the control point leading to the vertex `idx`. The returned position is relative to the vertex `idx`. If the index is out of bounds, the function sends an error to the console, and returns `(0, 0, 0)`.
200 	*/
201 	Vector3 getPointIn(in long idx) const
202 	{
203 		checkClassBinding!(typeof(this))();
204 		return ptrcall!(Vector3)(GDNativeClassBinding.getPointIn, _godot_object, idx);
205 	}
206 	/**
207 	Returns the position of the control point leading out of the vertex `idx`. The returned position is relative to the vertex `idx`. If the index is out of bounds, the function sends an error to the console, and returns `(0, 0, 0)`.
208 	*/
209 	Vector3 getPointOut(in long idx) const
210 	{
211 		checkClassBinding!(typeof(this))();
212 		return ptrcall!(Vector3)(GDNativeClassBinding.getPointOut, _godot_object, idx);
213 	}
214 	/**
215 	Returns the position of the vertex `idx`. If the index is out of bounds, the function sends an error to the console, and returns `(0, 0, 0)`.
216 	*/
217 	Vector3 getPointPosition(in long idx) const
218 	{
219 		checkClassBinding!(typeof(this))();
220 		return ptrcall!(Vector3)(GDNativeClassBinding.getPointPosition, _godot_object, idx);
221 	}
222 	/**
223 	Returns the tilt angle in radians for the point `idx`. If the index is out of bounds, the function sends an error to the console, and returns `0`.
224 	*/
225 	double getPointTilt(in long idx) const
226 	{
227 		checkClassBinding!(typeof(this))();
228 		return ptrcall!(double)(GDNativeClassBinding.getPointTilt, _godot_object, idx);
229 	}
230 	/**
231 	Returns the position between the vertex `idx` and the vertex `idx + 1`, where `t` controls if the point is the first vertex (`t = 0.0`), the last vertex (`t = 1.0`), or in between. Values of `t` outside the range (`0.0 >= t <=1`) give strange, but predictable results.
232 	If `idx` is out of bounds it is truncated to the first or last vertex, and `t` is ignored. If the curve has no points, the function sends an error to the console, and returns `(0, 0, 0)`.
233 	*/
234 	Vector3 interpolate(in long idx, in double t) const
235 	{
236 		checkClassBinding!(typeof(this))();
237 		return ptrcall!(Vector3)(GDNativeClassBinding.interpolate, _godot_object, idx, t);
238 	}
239 	/**
240 	Returns a point within the curve at position `offset`, where `offset` is measured as a distance in 3D units along the curve.
241 	To do that, it finds the two cached points where the `offset` lies between, then interpolates the values. This interpolation is cubic if `cubic` is set to `true`, or linear if set to `false`.
242 	Cubic interpolation tends to follow the curves better, but linear is faster (and often, precise enough).
243 	*/
244 	Vector3 interpolateBaked(in double offset, in bool cubic = false) const
245 	{
246 		checkClassBinding!(typeof(this))();
247 		return ptrcall!(Vector3)(GDNativeClassBinding.interpolateBaked, _godot_object, offset, cubic);
248 	}
249 	/**
250 	Returns an up vector within the curve at position `offset`, where `offset` is measured as a distance in 3D units along the curve.
251 	To do that, it finds the two cached up vectors where the `offset` lies between, then interpolates the values. If `apply_tilt` is `true`, an interpolated tilt is applied to the interpolated up vector.
252 	If the curve has no up vectors, the function sends an error to the console, and returns `(0, 1, 0)`.
253 	*/
254 	Vector3 interpolateBakedUpVector(in double offset, in bool apply_tilt = false) const
255 	{
256 		checkClassBinding!(typeof(this))();
257 		return ptrcall!(Vector3)(GDNativeClassBinding.interpolateBakedUpVector, _godot_object, offset, apply_tilt);
258 	}
259 	/**
260 	Returns the position at the vertex `fofs`. It calls $(D interpolate) using the integer part of `fofs` as `idx`, and its fractional part as `t`.
261 	*/
262 	Vector3 interpolatef(in double fofs) const
263 	{
264 		checkClassBinding!(typeof(this))();
265 		return ptrcall!(Vector3)(GDNativeClassBinding.interpolatef, _godot_object, fofs);
266 	}
267 	/**
268 	
269 	*/
270 	bool isUpVectorEnabled() const
271 	{
272 		checkClassBinding!(typeof(this))();
273 		return ptrcall!(bool)(GDNativeClassBinding.isUpVectorEnabled, _godot_object);
274 	}
275 	/**
276 	Deletes the point `idx` from the curve. Sends an error to the console if `idx` is out of bounds.
277 	*/
278 	void removePoint(in long idx)
279 	{
280 		checkClassBinding!(typeof(this))();
281 		ptrcall!(void)(GDNativeClassBinding.removePoint, _godot_object, idx);
282 	}
283 	/**
284 	
285 	*/
286 	void setBakeInterval(in double distance)
287 	{
288 		checkClassBinding!(typeof(this))();
289 		ptrcall!(void)(GDNativeClassBinding.setBakeInterval, _godot_object, distance);
290 	}
291 	/**
292 	Sets the position of the control point leading to the vertex `idx`. If the index is out of bounds, the function sends an error to the console. The position is relative to the vertex.
293 	*/
294 	void setPointIn(in long idx, in Vector3 position)
295 	{
296 		checkClassBinding!(typeof(this))();
297 		ptrcall!(void)(GDNativeClassBinding.setPointIn, _godot_object, idx, position);
298 	}
299 	/**
300 	Sets the position of the control point leading out of the vertex `idx`. If the index is out of bounds, the function sends an error to the console. The position is relative to the vertex.
301 	*/
302 	void setPointOut(in long idx, in Vector3 position)
303 	{
304 		checkClassBinding!(typeof(this))();
305 		ptrcall!(void)(GDNativeClassBinding.setPointOut, _godot_object, idx, position);
306 	}
307 	/**
308 	Sets the position for the vertex `idx`. If the index is out of bounds, the function sends an error to the console.
309 	*/
310 	void setPointPosition(in long idx, in Vector3 position)
311 	{
312 		checkClassBinding!(typeof(this))();
313 		ptrcall!(void)(GDNativeClassBinding.setPointPosition, _godot_object, idx, position);
314 	}
315 	/**
316 	Sets the tilt angle in radians for the point `idx`. If the index is out of bounds, the function sends an error to the console.
317 	The tilt controls the rotation along the look-at axis an object traveling the path would have. In the case of a curve controlling a $(D PathFollow), this tilt is an offset over the natural tilt the $(D PathFollow) calculates.
318 	*/
319 	void setPointTilt(in long idx, in double tilt)
320 	{
321 		checkClassBinding!(typeof(this))();
322 		ptrcall!(void)(GDNativeClassBinding.setPointTilt, _godot_object, idx, tilt);
323 	}
324 	/**
325 	
326 	*/
327 	void setUpVectorEnabled(in bool enable)
328 	{
329 		checkClassBinding!(typeof(this))();
330 		ptrcall!(void)(GDNativeClassBinding.setUpVectorEnabled, _godot_object, enable);
331 	}
332 	/**
333 	Returns a list of points along the curve, with a curvature controlled point density. That is, the curvier parts will have more points than the straighter parts.
334 	This approximation makes straight segments between each point, then subdivides those segments until the resulting shape is similar enough.
335 	`max_stages` controls how many subdivisions a curve segment may face before it is considered approximate enough. Each subdivision splits the segment in half, so the default 5 stages may mean up to 32 subdivisions per curve segment. Increase with care!
336 	`tolerance_degrees` controls how many degrees the midpoint of a segment may deviate from the real curve, before the segment has to be subdivided.
337 	*/
338 	PoolVector3Array tessellate(in long max_stages = 5, in double tolerance_degrees = 4) const
339 	{
340 		checkClassBinding!(typeof(this))();
341 		return ptrcall!(PoolVector3Array)(GDNativeClassBinding.tessellate, _godot_object, max_stages, tolerance_degrees);
342 	}
343 	/**
344 	
345 	*/
346 	@property Dictionary _data()
347 	{
348 		return _getData();
349 	}
350 	/// ditto
351 	@property void _data(Dictionary v)
352 	{
353 		_setData(v);
354 	}
355 	/**
356 	The distance in meters between two adjacent cached points. Changing it forces the cache to be recomputed the next time the $(D getBakedPoints) or $(D getBakedLength) function is called. The smaller the distance, the more points in the cache and the more memory it will consume, so use with care.
357 	*/
358 	@property double bakeInterval()
359 	{
360 		return getBakeInterval();
361 	}
362 	/// ditto
363 	@property void bakeInterval(double v)
364 	{
365 		setBakeInterval(v);
366 	}
367 	/**
368 	If `true`, the curve will bake up vectors used for orientation. This is used when $(D PathFollow.rotationMode) is set to $(D constant PathFollow.ROTATION_ORIENTED). Changing it forces the cache to be recomputed.
369 	*/
370 	@property bool upVectorEnabled()
371 	{
372 		return isUpVectorEnabled();
373 	}
374 	/// ditto
375 	@property void upVectorEnabled(bool v)
376 	{
377 		setUpVectorEnabled(v);
378 	}
379 }