doxygen: add newline after \file
[blender.git] / source / blender / blenkernel / BKE_fcurve.h
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  *
16  * The Original Code is Copyright (C) 2009 Blender Foundation, Joshua Leung
17  * All rights reserved.
18  */
19
20 #ifndef __BKE_FCURVE_H__
21 #define __BKE_FCURVE_H__
22
23 /** \file
24  * \ingroup bke
25  */
26
27 #ifdef __cplusplus
28 extern "C" {
29 #endif
30
31 struct ChannelDriver;
32 struct DriverTarget;
33 struct DriverVar;
34 struct FCM_EnvelopeData;
35 struct FCurve;
36 struct FModifier;
37
38 struct AnimData;
39 struct BezTriple;
40 struct PathResolvedRNA;
41 struct PointerRNA;
42 struct PropertyRNA;
43 struct StructRNA;
44 struct bAction;
45 struct bContext;
46
47 #include "DNA_curve_types.h"
48
49 /* ************** Keyframe Tools ***************** */
50
51 typedef struct CfraElem {
52         struct CfraElem *next, *prev;
53         float cfra;
54         int sel;
55 } CfraElem;
56
57 void bezt_add_to_cfra_elem(ListBase *lb, struct BezTriple *bezt);
58
59 /* ************** F-Curve Drivers ***************** */
60
61 /* With these iterators for convenience, the variables "tarIndex" and "dtar" can be
62  * accessed directly from the code using them, but it is not recommended that their
63  * values be changed to point at other slots...
64  */
65
66 /* convenience looper over ALL driver targets for a given variable (even the unused ones) */
67 #define DRIVER_TARGETS_LOOPER_BEGIN(dvar) \
68         { \
69                 DriverTarget *dtar = &dvar->targets[0]; \
70                 int tarIndex = 0; \
71                 for (; tarIndex < MAX_DRIVER_TARGETS; tarIndex++, dtar++)
72
73 /* convenience looper over USED driver targets only */
74 #define DRIVER_TARGETS_USED_LOOPER_BEGIN(dvar) \
75         { \
76                 DriverTarget *dtar = &dvar->targets[0]; \
77                 int tarIndex = 0; \
78                 for (; tarIndex < dvar->num_targets; tarIndex++, dtar++)
79
80 /* tidy up for driver targets loopers */
81 #define DRIVER_TARGETS_LOOPER_END \
82 } ((void)0)
83
84 /* ---------------------- */
85
86 void fcurve_free_driver(struct FCurve *fcu);
87 struct ChannelDriver *fcurve_copy_driver(const struct ChannelDriver *driver);
88
89 void driver_variables_copy(struct ListBase *dst_list, const struct ListBase *src_list);
90
91 void driver_free_variable(struct ListBase *variables, struct DriverVar *dvar);
92 void driver_free_variable_ex(struct ChannelDriver *driver, struct DriverVar *dvar);
93
94 void driver_change_variable_type(struct DriverVar *dvar, int type);
95 void driver_variable_name_validate(struct DriverVar *dvar);
96 struct DriverVar *driver_add_new_variable(struct ChannelDriver *driver);
97
98 float driver_get_variable_value(struct ChannelDriver *driver, struct DriverVar *dvar);
99 bool  driver_get_variable_property(
100         struct ChannelDriver *driver, struct DriverTarget *dtar,
101         struct PointerRNA *r_ptr, struct PropertyRNA **r_prop, int *r_index);
102
103 bool BKE_driver_has_simple_expression(struct ChannelDriver *driver);
104 void BKE_driver_invalidate_expression(struct ChannelDriver *driver, bool expr_changed, bool varname_changed);
105
106 float evaluate_driver(struct PathResolvedRNA *anim_rna, struct ChannelDriver *driver,
107                       struct ChannelDriver *driver_orig, const float evaltime);
108
109 /* ************** F-Curve Modifiers *************** */
110
111 typedef struct GHash FModifierStackStorage;
112
113 /* F-Curve Modifier Type-Info (fmi):
114  *  This struct provides function pointers for runtime, so that functions can be
115  *  written more generally (with fewer/no special exceptions for various modifiers).
116  *
117  *  Callers of these functions must check that they actually point to something useful,
118  *  as some constraints don't define some of these.
119  *
120  *  Warning: it is not too advisable to reorder order of members of this struct,
121  *           as you'll have to edit quite a few ($FMODIFIER_NUM_TYPES) of these
122  *           structs.
123  */
124 typedef struct FModifierTypeInfo {
125         /* admin/ident */
126         short type;             /* FMODIFIER_TYPE_### */
127         short size;             /* size in bytes of the struct */
128         short acttype;          /* eFMI_Action_Types */
129         short requires;         /* eFMI_Requirement_Flags */
130         char  name[64];          /* name of modifier in interface */
131         char  structName[64];    /* name of struct for SDNA */
132
133         /* data management function pointers - special handling */
134         /* free any data that is allocated separately (optional) */
135         void (*free_data)(struct FModifier *fcm);
136         /* copy any special data that is allocated separately (optional) */
137         void (*copy_data)(struct FModifier *fcm, const struct FModifier *src);
138         /* set settings for data that will be used for FCuModifier.data (memory already allocated using MEM_callocN) */
139         void (*new_data)(void *mdata);
140         /* verifies that the modifier settings are valid */
141         void (*verify_data)(struct FModifier *fcm);
142
143         /* evaluation */
144         /* evaluate time that the modifier requires the F-Curve to be evaluated at */
145         float (*evaluate_modifier_time)(struct FCurve *fcu, struct FModifier *fcm, float cvalue, float evaltime);
146         /* evaluate the modifier for the given time and 'accumulated' value */
147         void (*evaluate_modifier)(struct FCurve *fcu, struct FModifier *fcm, float *cvalue, float evaltime);
148
149         /* Same as above but for modifiers which requires storage */
150         float (*evaluate_modifier_time_storage)(FModifierStackStorage *storage, struct FCurve *fcu, struct FModifier *fcm, float cvalue, float evaltime);
151         void (*evaluate_modifier_storage)(FModifierStackStorage *storage, struct FCurve *fcu, struct FModifier *fcm, float *cvalue, float evaltime);
152 } FModifierTypeInfo;
153
154 /* Values which describe the behavior of a FModifier Type */
155 typedef enum eFMI_Action_Types {
156         /* modifier only modifies values outside of data range */
157         FMI_TYPE_EXTRAPOLATION = 0,
158         /* modifier leaves data-points alone, but adjusts the interpolation between and around them */
159         FMI_TYPE_INTERPOLATION,
160         /* modifier only modifies the values of points (but times stay the same) */
161         FMI_TYPE_REPLACE_VALUES,
162         /* modifier generates a curve regardless of what came before */
163         FMI_TYPE_GENERATE_CURVE
164 } eFMI_Action_Types;
165
166 /* Flags for the requirements of a FModifier Type */
167 typedef enum eFMI_Requirement_Flags {
168         /* modifier requires original data-points (kindof beats the purpose of a modifier stack?) */
169         FMI_REQUIRES_ORIGINAL_DATA      = (1 << 0),
170         /* modifier doesn't require on any preceding data (i.e. it will generate a curve).
171          * Use in conjunction with FMI_TYPE_GENRATE_CURVE
172          */
173         FMI_REQUIRES_NOTHING            = (1 << 1),
174         /* refer to modifier instance */
175         FMI_REQUIRES_RUNTIME_CHECK      = (1 << 2),
176
177         /* Requires to store data shared between time and valua evaluation */
178         FMI_REQUIRES_STORAGE            = (1 << 3),
179 } eFMI_Requirement_Flags;
180
181 /* Function Prototypes for FModifierTypeInfo's */
182 const FModifierTypeInfo *fmodifier_get_typeinfo(const struct FModifier *fcm);
183 const FModifierTypeInfo *get_fmodifier_typeinfo(const int type);
184
185 /* ---------------------- */
186
187 struct FModifier *add_fmodifier(ListBase *modifiers, int type, struct FCurve *owner_fcu);
188 struct FModifier *copy_fmodifier(const struct FModifier *src);
189 void copy_fmodifiers(ListBase *dst, const ListBase *src);
190 bool remove_fmodifier(ListBase *modifiers, struct FModifier *fcm);
191 void free_fmodifiers(ListBase *modifiers);
192
193 struct FModifier *find_active_fmodifier(ListBase *modifiers);
194 void set_active_fmodifier(ListBase *modifiers, struct FModifier *fcm);
195
196 bool list_has_suitable_fmodifier(ListBase *modifiers, int mtype, short acttype);
197
198 FModifierStackStorage *evaluate_fmodifiers_storage_new(ListBase *modifiers);
199 void evaluate_fmodifiers_storage_free(FModifierStackStorage *storage);
200 float evaluate_time_fmodifiers(FModifierStackStorage *storage, ListBase *modifiers, struct FCurve *fcu, float cvalue, float evaltime);
201 void evaluate_value_fmodifiers(FModifierStackStorage *storage, ListBase *modifiers, struct FCurve *fcu, float *cvalue, float evaltime);
202
203 void fcurve_bake_modifiers(struct FCurve *fcu, int start, int end);
204
205 int BKE_fcm_envelope_find_index(struct FCM_EnvelopeData *array, float frame, int arraylen, bool *r_exists);
206
207 /* ************** F-Curves API ******************** */
208
209 /* threshold for binary-searching keyframes - threshold here should be good enough for now, but should become userpref */
210 #define BEZT_BINARYSEARCH_THRESH   0.01f /* was 0.00001, but giving errors */
211
212 /* -------- Data Management  --------  */
213
214 void free_fcurve(struct FCurve *fcu);
215 struct FCurve *copy_fcurve(const struct FCurve *fcu);
216
217 void free_fcurves(ListBase *list);
218 void copy_fcurves(ListBase *dst, ListBase *src);
219
220 /* find matching F-Curve in the given list of F-Curves */
221 struct FCurve *list_find_fcurve(ListBase *list, const char rna_path[], const int array_index);
222
223 struct FCurve *iter_step_fcurve(struct FCurve *fcu_iter, const char rna_path[]);
224
225 /* high level function to get an fcurve from C without having the rna */
226 struct FCurve *id_data_find_fcurve(ID *id, void *data, struct StructRNA *type, const char *prop_name, int index, bool *r_driven);
227
228 /* Get list of LinkData's containing pointers to the F-Curves which control the types of data indicated
229  * e.g.  numMatches = list_find_data_fcurves(matches, &act->curves, "pose.bones[", "MyFancyBone");
230  */
231 int list_find_data_fcurves(ListBase *dst, ListBase *src, const char *dataPrefix, const char *dataName);
232
233 /* Find an f-curve based on an rna property. */
234 struct FCurve *rna_get_fcurve(
235         struct PointerRNA *ptr, struct PropertyRNA *prop, int rnaindex,
236         struct AnimData **r_adt, struct bAction **r_action,
237         bool *r_driven, bool *r_special);
238 /* Same as above, but takes a context data, temp hack needed for complex paths like texture ones. */
239 struct FCurve *rna_get_fcurve_context_ui(
240         struct bContext *C, struct PointerRNA *ptr, struct PropertyRNA *prop, int rnaindex,
241         struct AnimData **r_adt, struct bAction **r_action, bool *r_driven, bool *r_special);
242
243 /* Binary search algorithm for finding where to 'insert' BezTriple with given frame number.
244  * Returns the index to insert at (data already at that index will be offset if replace is 0)
245  */
246 int binarysearch_bezt_index(struct BezTriple array[], float frame, int arraylen, bool *r_replace);
247
248 /* get the time extents for F-Curve */
249 bool calc_fcurve_range(struct FCurve *fcu, float *min, float *max,
250                        const bool do_sel_only, const bool do_min_length);
251
252 /* get the bounding-box extents for F-Curve */
253 bool calc_fcurve_bounds(struct FCurve *fcu, float *xmin, float *xmax, float *ymin, float *ymax,
254                         const bool do_sel_only, const bool include_handles);
255
256 /* .............. */
257
258 /* Are keyframes on F-Curve of any use (to final result, and to show in editors)? */
259 bool fcurve_are_keyframes_usable(struct FCurve *fcu);
260
261 /* Can keyframes be added to F-Curve? */
262 bool fcurve_is_keyframable(struct FCurve *fcu);
263 bool BKE_fcurve_is_protected(struct FCurve *fcu);
264
265 /* The curve is an infinite cycle via Cycles modifier */
266 bool BKE_fcurve_is_cyclic(struct FCurve *fcu);
267
268 /* Type of infinite cycle for a curve. */
269 typedef enum eFCU_Cycle_Type {
270         FCU_CYCLE_NONE = 0,
271         /* The cycle repeats identically to the base range. */
272         FCU_CYCLE_PERFECT,
273         /* The cycle accumulates the change between start and end keys. */
274         FCU_CYCLE_OFFSET
275 } eFCU_Cycle_Type;
276
277 eFCU_Cycle_Type BKE_fcurve_get_cycle_type(struct FCurve *fcu);
278
279 /* -------- Curve Sanity --------  */
280
281 void calchandles_fcurve(struct FCurve *fcu);
282 void testhandles_fcurve(struct FCurve *fcu, const bool use_handle);
283 void sort_time_fcurve(struct FCurve *fcu);
284 short test_time_fcurve(struct FCurve *fcu);
285
286 void correct_bezpart(float v1[2], float v2[2], float v3[2], float v4[2]);
287
288 /* -------- Evaluation --------  */
289
290 /* evaluate fcurve */
291 float evaluate_fcurve(struct FCurve *fcu, float evaltime);
292 float evaluate_fcurve_only_curve(struct FCurve *fcu, float evaltime);
293 float evaluate_fcurve_driver(struct PathResolvedRNA *anim_rna, struct FCurve *fcu,
294                              struct ChannelDriver *driver_orig, float evaltime);
295 /* evaluate fcurve and store value */
296 float calculate_fcurve(struct PathResolvedRNA *anim_rna, struct FCurve *fcu, float evaltime);
297
298 /* ************* F-Curve Samples API ******************** */
299
300 /* -------- Defines --------  */
301
302 /* Basic signature for F-Curve sample-creation function
303  * - fcu: the F-Curve being operated on
304  * - data: pointer to some specific data that may be used by one of the callbacks
305  */
306 typedef float (*FcuSampleFunc)(struct FCurve *fcu, void *data, float evaltime);
307
308 /* ----- Sampling Callbacks ------  */
309
310 /* Basic sampling callback which acts as a wrapper for evaluate_fcurve() */
311 float fcurve_samplingcb_evalcurve(struct FCurve *fcu, void *data, float evaltime);
312
313 /* -------- Main Methods --------  */
314
315 /* Main API function for creating a set of sampled curve data, given some callback function
316  * used to retrieve the values to store.
317  */
318 void fcurve_store_samples(struct FCurve *fcu, void *data, int start, int end, FcuSampleFunc sample_cb);
319
320 #ifdef __cplusplus
321 }
322 #endif
323
324 #endif /* __BKE_FCURVE_H__*/