Merge with -r 22620:23107.
[blender.git] / source / blender / makesrna / intern / rna_boid.c
1 /**
2  * $Id$
3  *
4  * ***** BEGIN GPL LICENSE BLOCK *****
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version 2
9  * of the License, or (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software Foundation,
18  * Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
19  *
20  * The Original Code is Copyright (C) 2009 by Janne Karhu.
21  * All rights reserved.
22  *
23  * The Original Code is: all of this file.
24  *
25  * Contributor(s): none yet.
26  *
27  * ***** END GPL LICENSE BLOCK *****
28  */
29
30 #include <float.h>
31 #include <limits.h>
32 #include <stdlib.h>
33
34 #include "RNA_define.h"
35 #include "RNA_types.h"
36
37 #include "rna_internal.h"
38
39 #include "DNA_scene_types.h"
40 #include "DNA_boid_types.h"
41 #include "DNA_object_types.h"
42 #include "DNA_particle_types.h"
43
44 #include "WM_api.h"
45 #include "WM_types.h"
46
47 EnumPropertyItem boidrule_type_items[] ={
48         {eBoidRuleType_Goal, "GOAL", 0, "Goal", "Go to assigned object or loudest assigned signal source."},
49         {eBoidRuleType_Avoid, "AVOID", 0, "Avoid", "Get away from assigned object or loudest assigned signal source."},
50         {eBoidRuleType_AvoidCollision, "AVOID_COLLISION", 0, "Avoid Collision", "Monoeuver to avoid collisions with other boids and deflector objects in near future."},
51         {eBoidRuleType_Separate, "SEPARATE", 0, "Separate", "Keep from going through other boids."},
52         {eBoidRuleType_Flock, "FLOCK", 0, "Flock", "Move to center of neighbors and match their velocity."},
53         {eBoidRuleType_FollowLeader, "FOLLOW_LEADER", 0, "Follow Leader", "Follow a boid or assigned object."},
54         {eBoidRuleType_AverageSpeed, "AVERAGE_SPEED", 0, "Average Speed", "Maintain speed, flight level or wander."},
55         {eBoidRuleType_Fight, "FIGHT", 0, "Fight", "Go to closest enemy and attack when in range."},
56         //{eBoidRuleType_Protect, "PROTECT", 0, "Protect", "Go to enemy closest to target and attack when in range."},
57         //{eBoidRuleType_Hide, "HIDE", 0, "Hide", "Find a deflector move to it's other side from closest enemy."},
58         //{eBoidRuleType_FollowPath, "FOLLOW_PATH", 0, "Follow Path", "Move along a assigned curve or closest curve in a group."},
59         //{eBoidRuleType_FollowWall, "FOLLOW_WALL", 0, "Follow Wall", "Move next to a deflector object's in direction of it's tangent."},
60         {0, NULL, 0, NULL, NULL}};
61
62 EnumPropertyItem boidruleset_type_items[] ={
63         {eBoidRulesetType_Fuzzy, "FUZZY", 0, "Fuzzy", "Rules are gone through top to bottom. Only the first rule that effect above fuzziness threshold is evaluated."},
64         {eBoidRulesetType_Random, "RANDOM", 0, "Random", "A random rule is selected for each boid."},
65         {eBoidRulesetType_Average, "AVERAGE", 0, "Average", "All rules are averaged."},
66         {0, NULL, 0, NULL, NULL}};
67
68
69 #ifdef RNA_RUNTIME
70
71 #include "BKE_context.h"
72 #include "BKE_depsgraph.h"
73 #include "BKE_particle.h"
74
75 static void rna_Boids_reset(bContext *C, PointerRNA *ptr)
76 {
77         Scene *scene = CTX_data_scene(C);
78         ParticleSettings *part;
79
80         if(ptr->type==&RNA_ParticleSystem) {
81                 ParticleSystem *psys = (ParticleSystem*)ptr->data;
82                 Object *ob = psys_find_object(scene, psys);
83                 
84                 psys->recalc = PSYS_RECALC_RESET;
85
86                 if(ob)
87                         DAG_id_flush_update(&ob->id, OB_RECALC_DATA);
88         }
89         else {
90                 part = ptr->id.data;
91                 psys_flush_particle_settings(scene, part, PSYS_RECALC_RESET);
92         }
93
94         WM_event_add_notifier(C, NC_OBJECT|ND_PARTICLE_DATA, NULL);
95 }
96 static void rna_Boids_reset_deps(bContext *C, PointerRNA *ptr)
97 {
98         Scene *scene = CTX_data_scene(C);
99         ParticleSettings *part;
100
101         if(ptr->type==&RNA_ParticleSystem) {
102                 ParticleSystem *psys = (ParticleSystem*)ptr->data;
103                 Object *ob = psys_find_object(scene, psys);
104                 
105                 psys->recalc = PSYS_RECALC_RESET;
106
107                 if(ob)
108                         DAG_id_flush_update(&ob->id, OB_RECALC_DATA);
109         }
110         else {
111                 part = ptr->id.data;
112                 psys_flush_particle_settings(scene, part, PSYS_RECALC_RESET);
113                 DAG_scene_sort(scene);
114         }
115
116         WM_event_add_notifier(C, NC_OBJECT|ND_PARTICLE_DATA, NULL);
117 }
118
119 static StructRNA* rna_BoidRule_refine(struct PointerRNA *ptr)
120 {
121         BoidRule *rule= (BoidRule*)ptr->data;
122
123         switch(rule->type) {
124                 case eBoidRuleType_Goal:
125                         return &RNA_BoidRuleGoal;
126                 case eBoidRuleType_Avoid:
127                         return &RNA_BoidRuleAvoid;
128                 case eBoidRuleType_AvoidCollision:
129                         return &RNA_BoidRuleAvoidCollision;
130                 case eBoidRuleType_FollowLeader:
131                         return &RNA_BoidRuleFollowLeader;
132                 case eBoidRuleType_AverageSpeed:
133                         return &RNA_BoidRuleAverageSpeed;
134                 case eBoidRuleType_Fight:
135                         return &RNA_BoidRuleFight;
136                 default:
137                         return &RNA_BoidRule;
138         }
139 }
140
141 static char *rna_BoidRule_path(PointerRNA *ptr)
142 {
143         return BLI_sprintfN("rules[%s]", ((BoidRule*)ptr->data)->name);  // XXX not unique
144 }
145
146 static PointerRNA rna_BoidState_active_boid_rule_get(PointerRNA *ptr)
147 {
148         BoidState *state= (BoidState*)ptr->data;
149         BoidRule *rule = (BoidRule*)state->rules.first;
150
151         for(; rule; rule=rule->next) {
152                 if(rule->flag & BOIDRULE_CURRENT)
153                         return rna_pointer_inherit_refine(ptr, &RNA_BoidRule, rule);
154         }
155         return rna_pointer_inherit_refine(ptr, &RNA_BoidRule, NULL);
156 }
157 static void rna_BoidState_active_boid_rule_index_range(PointerRNA *ptr, int *min, int *max)
158 {
159         BoidState *state= (BoidState*)ptr->data;
160         *min= 0;
161         *max= BLI_countlist(&state->rules)-1;
162         *max= MAX2(0, *max);
163 }
164
165 static int rna_BoidState_active_boid_rule_index_get(PointerRNA *ptr)
166 {
167         BoidState *state= (BoidState*)ptr->data;
168         BoidRule *rule = (BoidRule*)state->rules.first;
169         int i=0;
170
171         for(; rule; rule=rule->next, i++) {
172                 if(rule->flag & BOIDRULE_CURRENT)
173                         return i;
174         }
175         return 0;
176 }
177
178 static void rna_BoidState_active_boid_rule_index_set(struct PointerRNA *ptr, int value)
179 {
180         BoidState *state= (BoidState*)ptr->data;
181         BoidRule *rule = (BoidRule*)state->rules.first;
182         int i=0;
183
184         for(; rule; rule=rule->next, i++) {
185                 if(i==value)
186                         rule->flag |= BOIDRULE_CURRENT;
187                 else
188                         rule->flag &= ~BOIDRULE_CURRENT;
189         }
190 }
191
192 static PointerRNA rna_BoidSettings_active_boid_state_get(PointerRNA *ptr)
193 {
194         BoidSettings *boids= (BoidSettings*)ptr->data;
195         BoidState *state = (BoidState*)boids->states.first;
196
197         for(; state; state=state->next) {
198                 if(state->flag & BOIDSTATE_CURRENT)
199                         return rna_pointer_inherit_refine(ptr, &RNA_BoidState, state);
200         }
201         return rna_pointer_inherit_refine(ptr, &RNA_BoidState, NULL);
202 }
203 static void rna_BoidSettings_active_boid_state_index_range(PointerRNA *ptr, int *min, int *max)
204 {
205         BoidSettings *boids= (BoidSettings*)ptr->data;
206         *min= 0;
207         *max= BLI_countlist(&boids->states)-1;
208         *max= MAX2(0, *max);
209 }
210
211 static int rna_BoidSettings_active_boid_state_index_get(PointerRNA *ptr)
212 {
213         BoidSettings *boids= (BoidSettings*)ptr->data;
214         BoidState *state = (BoidState*)boids->states.first;
215         int i=0;
216
217         for(; state; state=state->next, i++) {
218                 if(state->flag & BOIDSTATE_CURRENT)
219                         return i;
220         }
221         return 0;
222 }
223
224 static void rna_BoidSettings_active_boid_state_index_set(struct PointerRNA *ptr, int value)
225 {
226         BoidSettings *boids= (BoidSettings*)ptr->data;
227         BoidState *state = (BoidState*)boids->states.first;
228         int i=0;
229
230         for(; state; state=state->next, i++) {
231                 if(i==value)
232                         state->flag |= BOIDSTATE_CURRENT;
233                 else
234                         state->flag &= ~BOIDSTATE_CURRENT;
235         }
236 }
237
238 #else
239
240 static void rna_def_boidrule_goal(BlenderRNA *brna)
241 {
242         StructRNA *srna;
243         PropertyRNA *prop;
244
245         srna= RNA_def_struct(brna, "BoidRuleGoal", "BoidRule");
246         RNA_def_struct_ui_text(srna, "Goal", "");
247         RNA_def_struct_sdna(srna, "BoidRuleGoalAvoid");
248
249         prop= RNA_def_property(srna, "object", PROP_POINTER, PROP_NONE);
250         RNA_def_property_pointer_sdna(prop, NULL, "ob");
251         RNA_def_property_flag(prop, PROP_EDITABLE);
252         RNA_def_property_ui_text(prop, "Object", "Goal object.");
253         RNA_def_property_update(prop, 0, "rna_Boids_reset_deps");
254
255         prop= RNA_def_property(srna, "predict", PROP_BOOLEAN, PROP_NONE);
256         RNA_def_property_boolean_sdna(prop, NULL, "options", BRULE_GOAL_AVOID_PREDICT);
257         RNA_def_property_ui_text(prop, "Predict", "Predict target movement.");
258         RNA_def_property_update(prop, 0, "rna_Boids_reset");
259 }
260
261 static void rna_def_boidrule_avoid(BlenderRNA *brna)
262 {
263         StructRNA *srna;
264         PropertyRNA *prop;
265
266         srna= RNA_def_struct(brna, "BoidRuleAvoid", "BoidRule");
267         RNA_def_struct_ui_text(srna, "Avoid", "");
268         RNA_def_struct_sdna(srna, "BoidRuleGoalAvoid");
269
270         prop= RNA_def_property(srna, "object", PROP_POINTER, PROP_NONE);
271         RNA_def_property_pointer_sdna(prop, NULL, "ob");
272         RNA_def_property_flag(prop, PROP_EDITABLE);
273         RNA_def_property_ui_text(prop, "Object", "Object to avoid.");
274         RNA_def_property_update(prop, 0, "rna_Boids_reset_deps");
275
276         prop= RNA_def_property(srna, "predict", PROP_BOOLEAN, PROP_NONE);
277         RNA_def_property_boolean_sdna(prop, NULL, "options", BRULE_GOAL_AVOID_PREDICT);
278         RNA_def_property_ui_text(prop, "Predict", "Predict target movement.");
279         RNA_def_property_update(prop, 0, "rna_Boids_reset");
280
281         prop= RNA_def_property(srna, "fear_factor", PROP_FLOAT, PROP_NONE);
282         RNA_def_property_range(prop, 0.0f, 100.0f);
283         RNA_def_property_ui_text(prop, "Fear factor", "Avoid object if danger from it is above this threshol.");
284         RNA_def_property_update(prop, 0, "rna_Boids_reset");
285 }
286
287 static void rna_def_boidrule_avoid_collision(BlenderRNA *brna)
288 {
289         StructRNA *srna;
290         PropertyRNA *prop;
291
292         srna= RNA_def_struct(brna, "BoidRuleAvoidCollision", "BoidRule");
293         RNA_def_struct_ui_text(srna, "Avoid Collision", "");
294
295         prop= RNA_def_property(srna, "boids", PROP_BOOLEAN, PROP_NONE);
296         RNA_def_property_boolean_sdna(prop, NULL, "options", BRULE_ACOLL_WITH_BOIDS);
297         RNA_def_property_ui_text(prop, "Boids", "Avoid collision with other boids.");
298         RNA_def_property_update(prop, 0, "rna_Boids_reset");
299
300         prop= RNA_def_property(srna, "deflectors", PROP_BOOLEAN, PROP_NONE);
301         RNA_def_property_boolean_sdna(prop, NULL, "options", BRULE_ACOLL_WITH_DEFLECTORS);
302         RNA_def_property_ui_text(prop, "Deflectors", "Avoid collision with deflector objects.");
303         RNA_def_property_update(prop, 0, "rna_Boids_reset");
304
305         prop= RNA_def_property(srna, "look_ahead", PROP_FLOAT, PROP_NONE);
306         RNA_def_property_range(prop, 0.0f, 100.0f);
307         RNA_def_property_ui_text(prop, "Look ahead", "Time to look ahead in seconds.");
308         RNA_def_property_update(prop, 0, "rna_Boids_reset");
309 }
310
311 static void rna_def_boidrule_follow_leader(BlenderRNA *brna)
312 {
313         StructRNA *srna;
314         PropertyRNA *prop;
315
316         srna= RNA_def_struct(brna, "BoidRuleFollowLeader", "BoidRule");
317         RNA_def_struct_ui_text(srna, "Follow Leader", "");
318
319         prop= RNA_def_property(srna, "object", PROP_POINTER, PROP_NONE);
320         RNA_def_property_pointer_sdna(prop, NULL, "ob");
321         RNA_def_property_flag(prop, PROP_EDITABLE);
322         RNA_def_property_ui_text(prop, "Object", "Follow this object instead of a boid.");
323         RNA_def_property_update(prop, 0, "rna_Boids_reset_deps");
324
325         prop= RNA_def_property(srna, "distance", PROP_FLOAT, PROP_NONE);
326         RNA_def_property_range(prop, 0.0f, 100.0f);
327         RNA_def_property_ui_text(prop, "Distance", "Distance behind leader to follow.");
328         RNA_def_property_update(prop, 0, "rna_Boids_reset");
329
330         prop= RNA_def_property(srna, "queue_size", PROP_INT, PROP_NONE);
331         RNA_def_property_range(prop, 0.0f, 100.0f);
332         RNA_def_property_ui_text(prop, "Queue Size", "How many boids in a line.");
333         RNA_def_property_update(prop, 0, "rna_Boids_reset");
334
335         prop= RNA_def_property(srna, "line", PROP_BOOLEAN, PROP_NONE);
336         RNA_def_property_boolean_sdna(prop, NULL, "options", BRULE_LEADER_IN_LINE);
337         RNA_def_property_ui_text(prop, "Line", "Follow leader in a line.");
338         RNA_def_property_update(prop, 0, "rna_Boids_reset");
339 }
340
341 static void rna_def_boidrule_average_speed(BlenderRNA *brna)
342 {
343         StructRNA *srna;
344         PropertyRNA *prop;
345
346         srna= RNA_def_struct(brna, "BoidRuleAverageSpeed", "BoidRule");
347         RNA_def_struct_ui_text(srna, "Average Speed", "");
348
349         prop= RNA_def_property(srna, "wander", PROP_FLOAT, PROP_NONE);
350         RNA_def_property_range(prop, 0.0f, 1.0f);
351         RNA_def_property_ui_text(prop, "Wander", "How fast velocity's direction is randomized.");
352         RNA_def_property_update(prop, 0, "rna_Boids_reset");
353
354         prop= RNA_def_property(srna, "level", PROP_FLOAT, PROP_NONE);
355         RNA_def_property_range(prop, 0.0f, 1.0f);
356         RNA_def_property_ui_text(prop, "Level", "How much velocity's z-component is kept constant.");
357         RNA_def_property_update(prop, 0, "rna_Boids_reset");
358
359         prop= RNA_def_property(srna, "speed", PROP_FLOAT, PROP_NONE);
360         RNA_def_property_range(prop, 0.0f, 1.0f);
361         RNA_def_property_ui_text(prop, "Speed", "Percentage of maximum speed.");
362         RNA_def_property_update(prop, 0, "rna_Boids_reset");
363 }
364
365 static void rna_def_boidrule_fight(BlenderRNA *brna)
366 {
367         StructRNA *srna;
368         PropertyRNA *prop;
369
370         srna= RNA_def_struct(brna, "BoidRuleFight", "BoidRule");
371         RNA_def_struct_ui_text(srna, "Fight", "");
372
373         prop= RNA_def_property(srna, "distance", PROP_FLOAT, PROP_NONE);
374         RNA_def_property_range(prop, 0.0f, 100.0f);
375         RNA_def_property_ui_text(prop, "Fight Distance", "Attack boids at max this distance.");
376         RNA_def_property_update(prop, 0, "rna_Boids_reset");
377
378         prop= RNA_def_property(srna, "flee_distance", PROP_FLOAT, PROP_NONE);
379         RNA_def_property_range(prop, 0.0f, 100.0f);
380         RNA_def_property_ui_text(prop, "Flee Distance", "Flee to this distance.");
381         RNA_def_property_update(prop, 0, "rna_Boids_reset");
382 }
383
384 static void rna_def_boidrule(BlenderRNA *brna)
385 {
386         StructRNA *srna;
387         PropertyRNA *prop;
388         
389         /* data */
390         srna= RNA_def_struct(brna, "BoidRule", NULL);
391         RNA_def_struct_ui_text(srna , "Boid Rule", "");
392         RNA_def_struct_refine_func(srna, "rna_BoidRule_refine");
393         RNA_def_struct_path_func(srna, "rna_BoidRule_path");
394         
395         /* strings */
396         prop= RNA_def_property(srna, "name", PROP_STRING, PROP_NONE);
397         RNA_def_property_ui_text(prop, "Name", "Boid rule name.");
398         RNA_def_struct_name_property(srna, prop);
399         
400         /* enums */
401         prop= RNA_def_property(srna, "type", PROP_ENUM, PROP_NONE);
402         RNA_def_property_clear_flag(prop, PROP_EDITABLE);
403         RNA_def_property_enum_sdna(prop, NULL, "type");
404         RNA_def_property_enum_items(prop, boidrule_type_items);
405         RNA_def_property_ui_text(prop, "Type", "");
406         
407         /* flags */
408         prop= RNA_def_property(srna, "in_air", PROP_BOOLEAN, PROP_NONE);
409         RNA_def_property_boolean_sdna(prop, NULL, "flag", BOIDRULE_IN_AIR);
410         RNA_def_property_ui_text(prop, "In Air", "Use rule when boid is flying.");
411         RNA_def_property_update(prop, 0, "rna_Boids_reset");
412         
413         prop= RNA_def_property(srna, "on_land", PROP_BOOLEAN, PROP_NONE);
414         RNA_def_property_boolean_sdna(prop, NULL, "flag", BOIDRULE_ON_LAND);
415         RNA_def_property_ui_text(prop, "On Land", "Use rule when boid is on land.");
416         RNA_def_property_update(prop, 0, "rna_Boids_reset");
417         
418         //prop= RNA_def_property(srna, "expanded", PROP_BOOLEAN, PROP_NONE);
419         //RNA_def_property_boolean_sdna(prop, NULL, "mode", eModifierMode_Expanded);
420         //RNA_def_property_ui_text(prop, "Expanded", "Set modifier expanded in the user interface.");
421
422         /* types */
423         rna_def_boidrule_goal(brna);
424         rna_def_boidrule_avoid(brna);
425         rna_def_boidrule_avoid_collision(brna);
426         rna_def_boidrule_follow_leader(brna);
427         rna_def_boidrule_average_speed(brna);
428         rna_def_boidrule_fight(brna);
429 }
430
431 static void rna_def_boidstate(BlenderRNA *brna)
432 {
433         StructRNA *srna;
434         PropertyRNA *prop;
435
436         srna = RNA_def_struct(brna, "BoidState", NULL);
437         RNA_def_struct_ui_text(srna, "Boid State", "Boid state for boid physics.");
438
439         prop= RNA_def_property(srna, "name", PROP_STRING, PROP_NONE);
440         RNA_def_property_ui_text(prop, "Name", "Boid state name.");
441         RNA_def_struct_name_property(srna, prop);
442
443         prop= RNA_def_property(srna, "ruleset_type", PROP_ENUM, PROP_NONE);
444         RNA_def_property_enum_items(prop, boidruleset_type_items);
445         RNA_def_property_ui_text(prop, "Rule Evaluation", "How the rules in the list are evaluated.");
446
447         prop= RNA_def_property(srna, "rules", PROP_COLLECTION, PROP_NONE);
448         RNA_def_property_struct_type(prop, "BoidRule");
449         RNA_def_property_ui_text(prop, "Boid Rules", "");
450
451         prop= RNA_def_property(srna, "active_boid_rule", PROP_POINTER, PROP_NONE);
452         RNA_def_property_struct_type(prop, "BoidRule");
453         RNA_def_property_pointer_funcs(prop, "rna_BoidState_active_boid_rule_get", NULL, NULL);
454         RNA_def_property_ui_text(prop, "Active Boid Rule", "");
455
456         prop= RNA_def_property(srna, "active_boid_rule_index", PROP_INT, PROP_UNSIGNED);
457         RNA_def_property_int_funcs(prop, "rna_BoidState_active_boid_rule_index_get", "rna_BoidState_active_boid_rule_index_set", "rna_BoidState_active_boid_rule_index_range");
458         RNA_def_property_ui_text(prop, "Active Boid Rule Index", "");
459
460         prop= RNA_def_property(srna, "rule_fuzziness", PROP_FLOAT, PROP_NONE);
461         RNA_def_property_range(prop, 0.0, 1.0);
462         RNA_def_property_ui_text(prop, "Rule Fuzzines", "");
463         RNA_def_property_update(prop, 0, "rna_Boids_reset");
464
465         prop= RNA_def_property(srna, "volume", PROP_FLOAT, PROP_NONE);
466         RNA_def_property_range(prop, 0.0, 100.0);
467         RNA_def_property_ui_text(prop, "Volume", "");
468         RNA_def_property_update(prop, 0, "rna_Boids_reset");
469
470         prop= RNA_def_property(srna, "falloff", PROP_FLOAT, PROP_NONE);
471         RNA_def_property_range(prop, 0.0, 10.0);
472         RNA_def_property_ui_text(prop, "Falloff", "");
473         RNA_def_property_update(prop, 0, "rna_Boids_reset");
474 }
475 static void rna_def_boid_settings(BlenderRNA *brna)
476 {
477         StructRNA *srna;
478         PropertyRNA *prop;
479
480         srna = RNA_def_struct(brna, "BoidSettings", NULL);
481         RNA_def_struct_ui_text(srna, "Boid Settings", "Settings for boid physics.");
482
483         prop= RNA_def_property(srna, "landing_smoothness", PROP_FLOAT, PROP_NONE);
484         RNA_def_property_range(prop, 0.0, 10.0);
485         RNA_def_property_ui_text(prop, "Landing Smoothness", "How smoothly the boids land.");
486         RNA_def_property_update(prop, 0, "rna_Boids_reset");
487
488         prop= RNA_def_property(srna, "banking", PROP_FLOAT, PROP_NONE);
489         RNA_def_property_range(prop, 0.0, 2.0);
490         RNA_def_property_ui_text(prop, "Banking", "Amount of rotation around velocity vector on turns.");
491         RNA_def_property_update(prop, 0, "rna_Boids_reset");
492
493         prop= RNA_def_property(srna, "height", PROP_FLOAT, PROP_NONE);
494         RNA_def_property_range(prop, 0.0, 2.0);
495         RNA_def_property_ui_text(prop, "Height", "Boid height relative to particle size.");
496         RNA_def_property_update(prop, 0, "rna_Boids_reset");
497
498         /* states */
499         prop= RNA_def_property(srna, "states", PROP_COLLECTION, PROP_NONE);
500         RNA_def_property_struct_type(prop, "BoidState");
501         RNA_def_property_ui_text(prop, "Boid States", "");
502
503         prop= RNA_def_property(srna, "active_boid_state", PROP_POINTER, PROP_NONE);
504         RNA_def_property_struct_type(prop, "BoidRule");
505         RNA_def_property_pointer_funcs(prop, "rna_BoidSettings_active_boid_state_get", NULL, NULL);
506         RNA_def_property_ui_text(prop, "Active Boid Rule", "");
507
508         prop= RNA_def_property(srna, "active_boid_state_index", PROP_INT, PROP_UNSIGNED);
509         RNA_def_property_int_funcs(prop, "rna_BoidSettings_active_boid_state_index_get", "rna_BoidSettings_active_boid_state_index_set", "rna_BoidSettings_active_boid_state_index_range");
510         RNA_def_property_ui_text(prop, "Active Boid State Index", "");
511
512         /* character properties */
513         prop= RNA_def_property(srna, "health", PROP_FLOAT, PROP_NONE);
514         RNA_def_property_range(prop, 0.0, 100.0);
515         RNA_def_property_ui_text(prop, "Health", "Initial boid health when born.");
516         RNA_def_property_update(prop, 0, "rna_Boids_reset");
517
518         prop= RNA_def_property(srna, "strength", PROP_FLOAT, PROP_NONE);
519         RNA_def_property_range(prop, 0.0, 100.0);
520         RNA_def_property_ui_text(prop, "Strength", "Maximum caused damage on attack per second.");
521         RNA_def_property_update(prop, 0, "rna_Boids_reset");
522
523         prop= RNA_def_property(srna, "aggression", PROP_FLOAT, PROP_NONE);
524         RNA_def_property_range(prop, 0.0, 100.0);
525         RNA_def_property_ui_text(prop, "Aggression", "Boid will fight this times stronger enemy.");
526         RNA_def_property_update(prop, 0, "rna_Boids_reset");
527
528         prop= RNA_def_property(srna, "accuracy", PROP_FLOAT, PROP_NONE);
529         RNA_def_property_range(prop, 0.0, 1.0);
530         RNA_def_property_ui_text(prop, "Accuracy", "Accuracy of attack.");
531         RNA_def_property_update(prop, 0, "rna_Boids_reset");
532
533         prop= RNA_def_property(srna, "range", PROP_FLOAT, PROP_NONE);
534         RNA_def_property_range(prop, 0.0, 100.0);
535         RNA_def_property_ui_text(prop, "Range", "The maximum distance from which a boid can attack.");
536         RNA_def_property_update(prop, 0, "rna_Boids_reset");
537
538         /* physical properties */
539         prop= RNA_def_property(srna, "air_min_speed", PROP_FLOAT, PROP_NONE);
540         RNA_def_property_range(prop, 0.0, 1.0);
541         RNA_def_property_ui_text(prop, "Min Air Speed", "Minimum speed in air (relative to maximum speed).");
542         RNA_def_property_update(prop, 0, "rna_Boids_reset");
543
544         prop= RNA_def_property(srna, "air_max_speed", PROP_FLOAT, PROP_NONE);
545         RNA_def_property_range(prop, 0.0, 100.0);
546         RNA_def_property_ui_text(prop, "Max Air Speed", "Maximum speed in air.");
547         RNA_def_property_update(prop, 0, "rna_Boids_reset");
548
549         prop= RNA_def_property(srna, "air_max_acc", PROP_FLOAT, PROP_NONE);
550         RNA_def_property_range(prop, 0.0, 1.0);
551         RNA_def_property_ui_text(prop, "Max Air Acceleration", "Maximum acceleration in air (relative to maximum speed).");
552         RNA_def_property_update(prop, 0, "rna_Boids_reset");
553
554         prop= RNA_def_property(srna, "air_max_ave", PROP_FLOAT, PROP_NONE);
555         RNA_def_property_range(prop, 0.0, 1.0);
556         RNA_def_property_ui_text(prop, "Max Air Angular Velocity", "Maximum angular velocity in air (relative to 180 degrees).");
557         RNA_def_property_update(prop, 0, "rna_Boids_reset");
558
559         prop= RNA_def_property(srna, "air_personal_space", PROP_FLOAT, PROP_NONE);
560         RNA_def_property_range(prop, 0.0, 10.0);
561         RNA_def_property_ui_text(prop, "Air Personal Space", "Radius of boids personal space in air (% of particle size).");
562         RNA_def_property_update(prop, 0, "rna_Boids_reset");
563
564         prop= RNA_def_property(srna, "land_jump_speed", PROP_FLOAT, PROP_NONE);
565         RNA_def_property_range(prop, 0.0, 100.0);
566         RNA_def_property_ui_text(prop, "Jump Speed", "Maximum speed for jumping.");
567         RNA_def_property_update(prop, 0, "rna_Boids_reset");
568
569         prop= RNA_def_property(srna, "land_max_speed", PROP_FLOAT, PROP_NONE);
570         RNA_def_property_range(prop, 0.0, 100.0);
571         RNA_def_property_ui_text(prop, "Max Land Speed", "Maximum speed on land.");
572         RNA_def_property_update(prop, 0, "rna_Boids_reset");
573
574         prop= RNA_def_property(srna, "land_max_acc", PROP_FLOAT, PROP_NONE);
575         RNA_def_property_range(prop, 0.0, 1.0);
576         RNA_def_property_ui_text(prop, "Max Land Acceleration", "Maximum acceleration on land (relative to maximum speed).");
577         RNA_def_property_update(prop, 0, "rna_Boids_reset");
578
579         prop= RNA_def_property(srna, "land_max_ave", PROP_FLOAT, PROP_NONE);
580         RNA_def_property_range(prop, 0.0, 1.0);
581         RNA_def_property_ui_text(prop, "Max Land Angular Velocity", "Maximum angular velocity on land (relative to 180 degrees).");
582         RNA_def_property_update(prop, 0, "rna_Boids_reset");
583
584         prop= RNA_def_property(srna, "land_personal_space", PROP_FLOAT, PROP_NONE);
585         RNA_def_property_range(prop, 0.0, 10.0);
586         RNA_def_property_ui_text(prop, "Land Personal Space", "Radius of boids personal space on land (% of particle size).");
587         RNA_def_property_update(prop, 0, "rna_Boids_reset");
588
589         prop= RNA_def_property(srna, "land_stick_force", PROP_FLOAT, PROP_NONE);
590         RNA_def_property_range(prop, 0.0, 1000.0);
591         RNA_def_property_ui_text(prop, "Land Stick Force", "How strong a force must be to start effecting a boid on land.");
592         RNA_def_property_update(prop, 0, "rna_Boids_reset");
593
594         /* options */
595         prop= RNA_def_property(srna, "allow_flight", PROP_BOOLEAN, PROP_NONE);
596         RNA_def_property_boolean_sdna(prop, NULL, "options", BOID_ALLOW_FLIGHT);
597         RNA_def_property_ui_text(prop, "Allow Flight", "Allow boids to move in air.");
598         RNA_def_property_update(prop, 0, "rna_Boids_reset");
599
600         prop= RNA_def_property(srna, "allow_land", PROP_BOOLEAN, PROP_NONE);
601         RNA_def_property_boolean_sdna(prop, NULL, "options", BOID_ALLOW_LAND);
602         RNA_def_property_ui_text(prop, "Allow Land", "Allow boids to move on land.");
603         RNA_def_property_update(prop, 0, "rna_Boids_reset");
604
605         prop= RNA_def_property(srna, "allow_climb", PROP_BOOLEAN, PROP_NONE);
606         RNA_def_property_boolean_sdna(prop, NULL, "options", BOID_ALLOW_CLIMB);
607         RNA_def_property_ui_text(prop, "Allow Climbing", "Allow boids to climb goal objects.");
608         RNA_def_property_update(prop, 0, "rna_Boids_reset");
609 }
610
611 void RNA_def_boid(BlenderRNA *brna)
612 {
613         rna_def_boidrule(brna);
614         rna_def_boidstate(brna);
615         rna_def_boid_settings(brna);
616 }
617
618 #endif