diff options
author | Andre Susano Pinto <andresusanopinto@gmail.com> | 2009-07-02 06:59:43 +0400 |
---|---|---|
committer | Andre Susano Pinto <andresusanopinto@gmail.com> | 2009-07-02 06:59:43 +0400 |
commit | 2acac0ff997832f5a1b25fdaf36321a6e5d7c771 (patch) | |
tree | 622403467484aca3905e4f403f0de6c62f575d0a /source | |
parent | 1b557a61a53235f978262c52ac79fa16464bdd91 (diff) | |
parent | 84cd5a6cfbd607e73f8b2f522983520b18b1b63b (diff) |
Reverted incorrect merge (missing files)
svn up -r 21247
svn merge -r 21247:21246 . (<= revert incorrect: merge -r 21041:21243)
svn up
Diffstat (limited to 'source')
570 files changed, 23164 insertions, 9155 deletions
diff --git a/source/Makefile b/source/Makefile index 62eb25acbc1..2df57f58c73 100644 --- a/source/Makefile +++ b/source/Makefile @@ -115,16 +115,25 @@ ifneq ($(NAN_NO_KETSJI),true) COMLIB += $(OCGDIR)/gameengine/ketsji/$(DEBUG_DIR)libketsji.a COMLIB += $(OCGDIR)/gameengine/blconverter/$(DEBUG_DIR)libblconverter.a COMLIB += $(OCGDIR)/gameengine/blconverter/$(DEBUG_DIR)libblconverter.a + COMLIB += $(NAN_SOLID)/lib/libsolid.a + COMLIB += $(NAN_SOLID)/lib/libsolid_broad.a + COMLIB += $(NAN_SOLID)/lib/libsolid_complex.a + COMLIB += $(NAN_SOLID)/lib/libsolid_convex.a + COMLIB += $(OCGDIR)/gameengine/blphys/sumo/$(DEBUG_DIR)libsumo.a COMLIB += $(OCGDIR)/gameengine/blphys/fuzzics/$(DEBUG_DIR)libfuzzics.a COMLIB += $(NAN_QHULL)/lib/libqhull.a COMLIB += $(OCGDIR)/gameengine/blphys/dummy/$(DEBUG_DIR)libdummy.a COMLIB += $(OCGDIR)/gameengine/blphys/common/$(DEBUG_DIR)libcommon.a +# COMLIB += $(OCGDIR)/gameengine/blphys/sumo/$(DEBUG_DIR)libsumo.a COMLIB += $(OCGDIR)/gameengine/blphys/dummy/$(DEBUG_DIR)libdummy.a COMLIB += $(OCGDIR)/gameengine/ketsji/$(DEBUG_DIR)libketsji.a COMLIB += $(OCGDIR)/gameengine/blphys/common/$(DEBUG_DIR)libcommon.a +# COMLIB += $(OCGDIR)/gameengine/blphys/blode/$(DEBUG_DIR)libblode.a +# COMLIB += $(OCGDIR)/gameengine/blphys/sumo/$(DEBUG_DIR)libsumo.a COMLIB += $(OCGDIR)/gameengine/blphys/dummy/$(DEBUG_DIR)libdummy.a COMLIB += $(OCGDIR)/gameengine/blphys/blbullet/$(DEBUG_DIR)libblbullet.a COMLIB += $(OCGDIR)/gameengine/blphys/common/$(DEBUG_DIR)libcommon.a +# COMLIB += $(OCGDIR)/gameengine/blphys/sumo/$(DEBUG_DIR)libsumo.a COMLIB += $(OCGDIR)/gameengine/blphys/dummy/$(DEBUG_DIR)libdummy.a COMLIB += $(OCGDIR)/gameengine/ketsji/$(DEBUG_DIR)libketsji.a COMLIB += $(OCGDIR)/gameengine/logic/$(DEBUG_DIR)liblogic.a @@ -134,6 +143,8 @@ ifneq ($(NAN_NO_KETSJI),true) COMLIB += $(OCGDIR)/gameengine/expression/$(DEBUG_DIR)libexpression.a COMLIB += $(OCGDIR)/gameengine/scenegraph/$(DEBUG_DIR)libscenegraph.a COMLIB += $(OCGDIR)/gameengine/videotex/$(DEBUG_DIR)libvideotex.a +# COMLIB += $(OCGDIR)/sumo/$(DEBUG_DIR)libfuzzics.a +# COMLIB += $(OCGDIR)/sumo/$(DEBUG_DIR)libsolid.a COMLIB += $(NAN_MOTO)/lib/libmoto.a COMLIB += $(NAN_SND_LIBS) COMLIB += $(OCGDIR)/kernel/gen_system/$(DEBUG_DIR)libgen_system.a diff --git a/source/blender/CMakeLists.txt b/source/blender/CMakeLists.txt index a9e3d50211f..a53b15673e2 100644 --- a/source/blender/CMakeLists.txt +++ b/source/blender/CMakeLists.txt @@ -37,6 +37,7 @@ ADD_SUBDIRECTORY(imbuf/intern/cineon) ADD_SUBDIRECTORY(gpu) ADD_SUBDIRECTORY(makesdna) ADD_SUBDIRECTORY(makesrna) +ADD_SUBDIRECTORY(radiosity) ADD_SUBDIRECTORY(readblenfile) ADD_SUBDIRECTORY(render) ADD_SUBDIRECTORY(blenfont) diff --git a/source/blender/Makefile b/source/blender/Makefile index 31636f838c3..64eb1a2614b 100644 --- a/source/blender/Makefile +++ b/source/blender/Makefile @@ -31,7 +31,7 @@ include nan_definitions.mk DIRS = windowmanager editors blenloader readblenfile -DIRS += avi imbuf render blenlib blenkernel blenpluginapi +DIRS += avi imbuf render radiosity blenlib blenkernel blenpluginapi DIRS += makesdna makesrna DIRS += python nodes gpu DIRS += blenfont diff --git a/source/blender/SConscript b/source/blender/SConscript index a064850c170..691fbf9b494 100644 --- a/source/blender/SConscript +++ b/source/blender/SConscript @@ -13,6 +13,7 @@ SConscript(['avi/SConscript', 'imbuf/intern/cineon/SConscript', 'makesdna/SConscript', 'makesrna/SConscript', + 'radiosity/SConscript', 'readblenfile/SConscript', 'render/SConscript', 'nodes/SConscript', diff --git a/source/blender/blenfont/BLF_api.h b/source/blender/blenfont/BLF_api.h index 2ee31a17fa6..e871de490f3 100644 --- a/source/blender/blenfont/BLF_api.h +++ b/source/blender/blenfont/BLF_api.h @@ -91,21 +91,6 @@ void BLF_enable(int option); void BLF_disable(int option); /* - * Shadow options, level is the blur level, can be 3, 5 or 0 and - * the other argument are the rgba color. - * Take care that shadow need to be enable using BLF_enable!!. - */ -void BLF_shadow(int level, float r, float g, float b, float a); - -/* - * Set the offset for shadow text, this is the current cursor - * position plus this offset, don't need call BLF_position before - * this function, the current position is calculate only on - * BLF_draw, so it's safe call this whenever you like. - */ -void BLF_shadow_offset(int x, int y); - -/* * Search the path directory to the locale files, this try all * the case for Linux, Win and Mac. */ @@ -134,8 +119,6 @@ void BLF_dir_free(char **dirs, int count); #define BLF_CLIPPING (1<<1) #define BLF_FONT_KERNING (1<<2) #define BLF_USER_KERNING (1<<3) -#define BLF_SHADOW (1<<4) -#define BLF_OVERLAP_CHAR (1<<5) /* font->mode. */ #define BLF_MODE_TEXTURE 0 diff --git a/source/blender/blenfont/intern/blf.c b/source/blender/blenfont/intern/blf.c index 9dad5a4bfa0..f06c7fb0d28 100644 --- a/source/blender/blenfont/intern/blf.c +++ b/source/blender/blenfont/intern/blf.c @@ -500,28 +500,3 @@ void BLF_kerning(float space) if (font) font->kerning= space; } - -void BLF_shadow(int level, float r, float g, float b, float a) -{ - FontBLF *font; - - font= global_font[global_font_cur]; - if (font) { - font->shadow= level; - font->shadow_col[0]= r; - font->shadow_col[1]= g; - font->shadow_col[2]= b; - font->shadow_col[3]= a; - } -} - -void BLF_shadow_offset(int x, int y) -{ - FontBLF *font; - - font= global_font[global_font_cur]; - if (font) { - font->shadow_x= x; - font->shadow_y= y; - } -} diff --git a/source/blender/blenfont/intern/blf_dir.c b/source/blender/blenfont/intern/blf_dir.c index 92dfe8457b0..88b0105a292 100644 --- a/source/blender/blenfont/intern/blf_dir.c +++ b/source/blender/blenfont/intern/blf_dir.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: blf_dir.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenfont/intern/blf_font.c b/source/blender/blenfont/intern/blf_font.c index a3c5232cc76..ee4ba0ee71a 100644 --- a/source/blender/blenfont/intern/blf_font.c +++ b/source/blender/blenfont/intern/blf_font.c @@ -146,22 +146,20 @@ void blf_font_draw(FontBLF *font, char *str) if (FT_Get_Kerning(font->face, g_prev_index, glyph_index, FT_KERNING_UNFITTED, &delta) == 0) { pen_x += delta.x >> 6; - - if (font->flags & BLF_OVERLAP_CHAR) { - if (pen_x < old_pen_x) - pen_x= old_pen_x; - } +/* + if (pen_x < old_pen_x) + pen_x= old_pen_x; +*/ } } if (font->flags & BLF_USER_KERNING) { old_pen_x= pen_x; pen_x += font->kerning; - - if (font->flags & BLF_OVERLAP_CHAR) { - if (pen_x < old_pen_x) - pen_x= old_pen_x; - } +/* + if (pen_x < old_pen_x) + pen_x= old_pen_x; +*/ } /* do not return this loop if clipped, we want every character tested */ @@ -230,22 +228,20 @@ void blf_font_boundbox(FontBLF *font, char *str, rctf *box) if (FT_Get_Kerning(font->face, g_prev_index, glyph_index, FT_KERNING_UNFITTED, &delta) == 0) { pen_x += delta.x >> 6; - - if (font->flags & BLF_OVERLAP_CHAR) { - if (pen_x < old_pen_x) - pen_x= old_pen_x; - } +/* + if (pen_x < old_pen_x) + old_pen_x= pen_x; +*/ } } if (font->flags & BLF_USER_KERNING) { old_pen_x= pen_x; pen_x += font->kerning; - - if (font->flags & BLF_OVERLAP_CHAR) { - if (pen_x < old_pen_x) - pen_x= old_pen_x; - } +/* + if (pen_x < old_pen_x) + old_pen_x= pen_x; +*/ } gbox.xmin= g->box.xmin + pen_x; diff --git a/source/blender/blenfont/intern/blf_glyph.c b/source/blender/blenfont/intern/blf_glyph.c index a637774d7bf..33a435cc5be 100644 --- a/source/blender/blenfont/intern/blf_glyph.c +++ b/source/blender/blenfont/intern/blf_glyph.c @@ -496,20 +496,8 @@ int blf_glyph_texture_render(FontBLF *font, GlyphBLF *g, float x, float y) GLint cur_tex; float dx, dx1; float y1, y2; - float xo, yo; - float color[4]; gt= g->tex_data; - xo= 0.0f; - yo= 0.0f; - - if (font->flags & BLF_SHADOW) { - xo= x; - yo= y; - x += font->shadow_x; - y += font->shadow_y; - } - dx= floor(x + gt->pos_x); dx1= dx + gt->width; y1= y + gt->pos_y; @@ -530,27 +518,6 @@ int blf_glyph_texture_render(FontBLF *font, GlyphBLF *g, float x, float y) if (cur_tex != gt->tex) glBindTexture(GL_TEXTURE_2D, gt->tex); - if (font->flags & BLF_SHADOW) { - glGetFloatv(GL_CURRENT_COLOR, color); - glColor4fv(font->shadow_col); - - if (font->shadow == 3) - blf_texture3_draw(gt->uv, dx, y1, dx1, y2); - else if (font->shadow == 5) - blf_texture5_draw(gt->uv, dx, y1, dx1, y2); - else - blf_texture_draw(gt->uv, dx, y1, dx1, y2); - - glColor4fv(color); - x= xo; - y= yo; - - dx= floor(x + gt->pos_x); - dx1= dx + gt->width; - y1= y + gt->pos_y; - y2= y + gt->pos_y - gt->height; - } - if (font->blur==3) blf_texture3_draw(gt->uv, dx, y1, dx1, y2); else if (font->blur==5) diff --git a/source/blender/blenfont/intern/blf_internal.h b/source/blender/blenfont/intern/blf_internal.h index c9bdc428ebb..af237690b58 100644 --- a/source/blender/blenfont/intern/blf_internal.h +++ b/source/blender/blenfont/intern/blf_internal.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: blf_internal.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenfont/intern/blf_internal_types.h b/source/blender/blenfont/intern/blf_internal_types.h index 5382ac19aae..ba988c522f0 100644 --- a/source/blender/blenfont/intern/blf_internal_types.h +++ b/source/blender/blenfont/intern/blf_internal_types.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: blf_internal_types.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -154,16 +154,6 @@ typedef struct FontBLF { /* blur: 3 or 5 large kernel */ int blur; - - /* shadow level. */ - int shadow; - - /* and shadow offset. */ - int shadow_x; - int shadow_y; - - /* shadow color. */ - float shadow_col[4]; /* this is the matrix that we load before rotate/scale/translate. */ float mat[4][4]; diff --git a/source/blender/blenfont/intern/blf_lang.c b/source/blender/blenfont/intern/blf_lang.c index 024172d6db4..757a18f0165 100644 --- a/source/blender/blenfont/intern/blf_lang.c +++ b/source/blender/blenfont/intern/blf_lang.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: blf_lang.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenkernel/BKE_cloth.h b/source/blender/blenkernel/BKE_cloth.h index 4270c677338..e09be838f06 100644 --- a/source/blender/blenkernel/BKE_cloth.h +++ b/source/blender/blenkernel/BKE_cloth.h @@ -46,7 +46,6 @@ #include "DNA_meshdata_types.h" #include "DNA_modifier_types.h" #include "DNA_object_types.h" -#include "DNA_scene_types.h" #include "BKE_collision.h" @@ -246,8 +245,8 @@ void bvhtree_update_from_cloth ( ClothModifierData *clmd, int moving ); void bvhselftree_update_from_cloth ( ClothModifierData *clmd, int moving ); // needed for editmesh.c -void cloth_write_cache( Object *ob, ClothModifierData *clmd, int framenr ); -int cloth_read_cache( Scene *scene, Object *ob, ClothModifierData *clmd, float framenr, int *old_framenr ); +void cloth_write_cache ( Object *ob, ClothModifierData *clmd, float framenr ); +int cloth_read_cache ( Object *ob, ClothModifierData *clmd, float framenr ); // needed for button_object.c void cloth_clear_cache ( Object *ob, ClothModifierData *clmd, float framenr ); diff --git a/source/blender/blenkernel/BKE_context.h b/source/blender/blenkernel/BKE_context.h index f536e117b7b..1845665a96d 100644 --- a/source/blender/blenkernel/BKE_context.h +++ b/source/blender/blenkernel/BKE_context.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BKE_context.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -131,7 +131,6 @@ void CTX_wm_menu_set(bContext *C, struct ARegion *menu); - the dir listbase consits of LinkData items */ PointerRNA CTX_data_pointer_get(const bContext *C, const char *member); -PointerRNA CTX_data_pointer_get_type(const bContext *C, const char *member, StructRNA *type); ListBase CTX_data_collection_get(const bContext *C, const char *member); ListBase CTX_data_dir_get(const bContext *C); void CTX_data_get(const bContext *C, const char *member, PointerRNA *r_ptr, ListBase *r_lb); diff --git a/source/blender/blenkernel/BKE_exotic.h b/source/blender/blenkernel/BKE_exotic.h index 5c47eeabfe8..11dc1f41109 100644 --- a/source/blender/blenkernel/BKE_exotic.h +++ b/source/blender/blenkernel/BKE_exotic.h @@ -47,6 +47,7 @@ int BKE_read_exotic(struct Scene *scene, char *name); void write_dxf(struct Scene *scene, char *str); void write_vrml(struct Scene *scene, char *str); +void write_videoscape(struct Scene *scene, char *str); void write_stl(struct Scene *scene, char *str); #endif diff --git a/source/blender/blenkernel/BKE_gpencil.h b/source/blender/blenkernel/BKE_gpencil.h index 1892c8e71a4..581285be21c 100644 --- a/source/blender/blenkernel/BKE_gpencil.h +++ b/source/blender/blenkernel/BKE_gpencil.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BDR_gpencil.h 19541 2009-04-05 06:54:47Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenkernel/BKE_material.h b/source/blender/blenkernel/BKE_material.h index 382754ee2b2..38a1d9b13b7 100644 --- a/source/blender/blenkernel/BKE_material.h +++ b/source/blender/blenkernel/BKE_material.h @@ -39,8 +39,6 @@ struct Material; struct ID; struct Object; -/* materials */ - void init_def_material(void); void free_material(struct Material *sc); void test_object_materials(struct ID *id); @@ -49,22 +47,15 @@ struct Material *add_material(char *name); struct Material *copy_material(struct Material *ma); void make_local_material(struct Material *ma); -void automatname(struct Material *); - -/* material slots */ - struct Material ***give_matarar(struct Object *ob); short *give_totcolp(struct Object *ob); struct Material *give_current_material(struct Object *ob, int act); struct ID *material_from(struct Object *ob, int act); void assign_material(struct Object *ob, struct Material *ma, int act); +void new_material_to_objectdata(struct Object *ob); int find_material_index(struct Object *ob, struct Material *ma); -void object_add_material_slot(struct Object *ob); -void object_remove_material_slot(struct Object *ob); - -/* rendering */ void init_render_material(struct Material *, int, float *); void init_render_materials(int, float *); @@ -73,8 +64,12 @@ void end_render_materials(void); int material_in_material(struct Material *parmat, struct Material *mat); +void automatname(struct Material *); +void delete_material_index(struct Object *ob); + void ramp_blend(int type, float *r, float *g, float *b, float fac, float *col); + #ifdef __cplusplus } #endif diff --git a/source/blender/blenkernel/BKE_particle.h b/source/blender/blenkernel/BKE_particle.h index 4d9916b9557..4efd9a7f8ba 100644 --- a/source/blender/blenkernel/BKE_particle.h +++ b/source/blender/blenkernel/BKE_particle.h @@ -217,8 +217,6 @@ char *psys_menu_string(struct Object *ob, int for_sb); struct ParticleSystem *psys_get_current(struct Object *ob); short psys_get_current_num(struct Object *ob); -void psys_set_current_num(Object *ob, int index); -struct Object *psys_find_object(struct Scene *scene, struct ParticleSystem *psys); //struct ParticleSystem *psys_get(struct Object *ob, int index); struct ParticleData *psys_get_selected_particle(struct ParticleSystem *psys, int *index); struct ParticleKey *psys_get_selected_key(struct ParticleSystem *psys, int pa_index, int *key_index); @@ -251,8 +249,6 @@ void copy_particle_key(struct ParticleKey *to, struct ParticleKey *from, int tim void psys_particle_on_emitter(struct ParticleSystemModifierData *psmd, int distr, int index, int index_dmcache, float *fuv, float foffset, float *vec, float *nor, float *utan, float *vtan, float *orco, float *ornor); struct ParticleSystemModifierData *psys_get_modifier(struct Object *ob, struct ParticleSystem *psys); -void object_add_particle_system_slot(struct Scene *scene, struct Object *ob); -void object_remove_particle_system_slot(struct Scene *scene, struct Object *ob); struct ParticleSettings *psys_new_settings(char *name, struct Main *main); struct ParticleSettings *psys_copy_settings(struct ParticleSettings *part); void psys_flush_particle_settings(struct Scene *scene, struct ParticleSettings *part, int recalc); @@ -294,13 +290,10 @@ void psys_get_reactor_target(struct Object *ob, struct ParticleSystem *psys, str void psys_init_effectors(struct Scene *scene, struct Object *obsrc, struct Group *group, struct ParticleSystem *psys); void psys_end_effectors(struct ParticleSystem *psys); -void psys_get_pointcache_start_end(struct Scene *scene, struct ParticleSystem *psys, int *sfra, int *efra); - void particle_system_update(struct Scene *scene, struct Object *ob, struct ParticleSystem *psys); /* ----------- functions needed only inside particlesystem ------------ */ /* particle.c */ -void psys_interpolate_particle(short type, struct ParticleKey keys[4], float dt, struct ParticleKey *result, int velocity); void psys_key_to_object(struct Object *ob, struct ParticleKey *key, float imat[][4]); //void psys_key_to_geometry(struct DerivedMesh *dm, struct ParticleData *pa, struct ParticleKey *key); //void psys_key_from_geometry(struct DerivedMesh *dm, struct ParticleData *pa, struct ParticleKey *key); diff --git a/source/blender/blenkernel/BKE_pointcache.h b/source/blender/blenkernel/BKE_pointcache.h index 3f1c45d28ec..8ef3ff4d4b7 100644 --- a/source/blender/blenkernel/BKE_pointcache.h +++ b/source/blender/blenkernel/BKE_pointcache.h @@ -31,8 +31,6 @@ #include "DNA_ID.h" -#include "MEM_guardedalloc.h" - /* Point cache clearing option, for BKE_ptcache_id_clear, before * and after are non inclusive (they wont remove the cfra) */ #define PTCACHE_CLEAR_ALL 0 @@ -44,7 +42,6 @@ #define PTCACHE_RESET_DEPSGRAPH 0 #define PTCACHE_RESET_BAKED 1 #define PTCACHE_RESET_OUTDATED 2 -#define PTCACHE_RESET_FREE 3 /* Add the blendfile name after blendcache_ */ #define PTCACHE_EXT ".bphys" @@ -59,11 +56,6 @@ #define PTCACHE_TYPE_PARTICLES 1 #define PTCACHE_TYPE_CLOTH 2 -/* PTCache read return code */ -#define PTCACHE_READ_EXACT 1 -#define PTCACHE_READ_INTERPOLATED 2 -#define PTCACHE_READ_OLD 3 - /* Structs */ struct Object; struct Scene; @@ -88,40 +80,6 @@ typedef struct PTCacheID { struct PointCache *cache; } PTCacheID; -typedef struct PTCacheWriter { - struct PTCacheID *pid; - int cfra; - int totelem; - - void (*set_elem)(int index, void *calldata, float *data); - void *calldata; -} PTCacheWriter; - -typedef struct PTCacheReader { - struct Scene *scene; - struct PTCacheID *pid; - float cfra; - int totelem; - - void (*set_elem)(int elem_index, void *calldata, float *data); - void (*interpolate_elem)(int index, void *calldata, float frs_sec, float cfra, float cfra1, float cfra2, float *data1, float *data2); - void *calldata; - - int *old_frame; -} PTCacheReader; - -typedef struct PTCacheBaker { - struct Scene *scene; - int bake; - int render; - int quick_step; - struct PTCacheID *pid; - int (*break_test)(void *data); - void *break_data; - void (*progressbar)(void *data, int num); - void *progresscontext; -} PTCacheBaker; - /* Creating ID's */ void BKE_ptcache_id_from_softbody(PTCacheID *pid, struct Object *ob, struct SoftBody *sb); void BKE_ptcache_id_from_particles(PTCacheID *pid, struct Object *ob, struct ParticleSystem *psys); @@ -135,9 +93,9 @@ void BKE_ptcache_remove(void); /* ID specific functions */ void BKE_ptcache_id_clear(PTCacheID *id, int mode, int cfra); int BKE_ptcache_id_exist(PTCacheID *id, int cfra); -int BKE_ptcache_id_reset(struct Scene *scene, PTCacheID *id, int mode); +int BKE_ptcache_id_reset(PTCacheID *id, int mode); void BKE_ptcache_id_time(PTCacheID *pid, struct Scene *scene, float cfra, int *startframe, int *endframe, float *timescale); -int BKE_ptcache_object_reset(struct Scene *scene, struct Object *ob, int mode); +int BKE_ptcache_object_reset(struct Object *ob, int mode); /* File reading/writing */ PTCacheFile *BKE_ptcache_file_open(PTCacheID *id, int mode, int cfra); @@ -145,12 +103,6 @@ void BKE_ptcache_file_close(PTCacheFile *pf); int BKE_ptcache_file_read_floats(PTCacheFile *pf, float *f, int tot); int BKE_ptcache_file_write_floats(PTCacheFile *pf, float *f, int tot); -void BKE_ptcache_update_info(PTCacheID *pid); - -/* General cache reading/writing */ -int BKE_ptcache_read_cache(PTCacheReader *reader); -int BKE_ptcache_write_cache(PTCacheWriter *writer); - /* Continue physics */ void BKE_ptcache_set_continue_physics(struct Scene *scene, int enable); int BKE_ptcache_get_continue_physics(void); @@ -160,9 +112,4 @@ struct PointCache *BKE_ptcache_add(void); void BKE_ptcache_free(struct PointCache *cache); struct PointCache *BKE_ptcache_copy(struct PointCache *cache); -/* Baking */ -void BKE_ptcache_quick_cache_all(struct Scene *scene); -void BKE_ptcache_make_cache(struct PTCacheBaker* baker); -void BKE_ptcache_toggle_disk_cache(struct PTCacheID *pid); - #endif diff --git a/source/blender/blenkernel/BKE_report.h b/source/blender/blenkernel/BKE_report.h index 21221026b8b..60e48004fb1 100644 --- a/source/blender/blenkernel/BKE_report.h +++ b/source/blender/blenkernel/BKE_report.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BKE_report.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenkernel/BKE_sequence.h b/source/blender/blenkernel/BKE_sequence.h index 65a3b0216fe..93f68f00d2f 100644 --- a/source/blender/blenkernel/BKE_sequence.h +++ b/source/blender/blenkernel/BKE_sequence.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BKE_sequence.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenkernel/BKE_utildefines.h b/source/blender/blenkernel/BKE_utildefines.h index 419f0f5beeb..6584af085cd 100644 --- a/source/blender/blenkernel/BKE_utildefines.h +++ b/source/blender/blenkernel/BKE_utildefines.h @@ -130,7 +130,7 @@ #define IN_RANGE(a, b, c) ((b < c)? ((b<a && a<c)? 1:0) : ((c<a && a<b)? 1:0)) /* this weirdo pops up in two places ... */ -#if !defined(WIN32) +#if !defined(WIN32) && !defined(__BeOS) #ifndef O_BINARY #define O_BINARY 0 #endif @@ -148,6 +148,12 @@ #define ID_NEW(a) if( (a) && (a)->id.newid ) (a)= (void *)(a)->id.newid #define FORM MAKE_ID('F','O','R','M') +#define DDG1 MAKE_ID('3','D','G','1') +#define DDG2 MAKE_ID('3','D','G','2') +#define DDG3 MAKE_ID('3','D','G','3') +#define DDG4 MAKE_ID('3','D','G','4') + +#define GOUR MAKE_ID('G','O','U','R') #define BLEN MAKE_ID('B','L','E','N') #define DER_ MAKE_ID('D','E','R','_') diff --git a/source/blender/blenkernel/intern/anim_sys.c b/source/blender/blenkernel/intern/anim_sys.c index 441e17f3318..30dcb383ef6 100644 --- a/source/blender/blenkernel/intern/anim_sys.c +++ b/source/blender/blenkernel/intern/anim_sys.c @@ -43,7 +43,6 @@ static short id_has_animdata (ID *id) case ID_OB: case ID_CU: case ID_KE: - case ID_PA: case ID_MA: case ID_TE: case ID_NT: case ID_LA: case ID_CA: case ID_WO: case ID_SCE: @@ -884,9 +883,6 @@ void BKE_animsys_evaluate_all_animation (Main *main, float ctime) /* meshes */ // TODO... - /* particles */ - EVAL_ANIM_IDS(main->particle.first, ADT_RECALC_ANIM); - /* objects */ /* ADT_RECALC_ANIM doesn't need to be supplied here, since object AnimData gets * this tagged by Depsgraph on framechange diff --git a/source/blender/blenkernel/intern/blender.c b/source/blender/blenkernel/intern/blender.c index d3d21018c1c..5fc7d18689d 100644 --- a/source/blender/blenkernel/intern/blender.c +++ b/source/blender/blenkernel/intern/blender.c @@ -221,6 +221,7 @@ static void clear_global(void) { // extern short winqueue_break; /* screen.c */ +// XXX freeAllRad(); fastshade_free_render(); /* lamps hang otherwise */ free_main(G.main); /* free all lib data */ diff --git a/source/blender/blenkernel/intern/cloth.c b/source/blender/blenkernel/intern/cloth.c index 08caea565aa..e98d7bb01a4 100644 --- a/source/blender/blenkernel/intern/cloth.c +++ b/source/blender/blenkernel/intern/cloth.c @@ -33,7 +33,6 @@ #include "DNA_mesh_types.h" #include "DNA_object_force.h" #include "DNA_scene_types.h" -#include "DNA_particle_types.h" #include "BKE_deform.h" #include "BKE_DerivedMesh.h" @@ -43,7 +42,6 @@ #include "BKE_object.h" #include "BKE_modifier.h" #include "BKE_utildefines.h" -#include "BKE_particle.h" #include "BKE_pointcache.h" @@ -341,99 +339,78 @@ void bvhselftree_update_from_cloth(ClothModifierData *clmd, int moving) } int modifiers_indexInObject(Object *ob, ModifierData *md_seek); -static void cloth_write_state(int index, Cloth *cloth, float *data) -{ - ClothVertex *vert = cloth->verts + index; - - memcpy(data, vert->x, 3 * sizeof(float)); - memcpy(data + 3, vert->xconst, 3 * sizeof(float)); - memcpy(data + 6, vert->v, 3 * sizeof(float)); -} -static void cloth_read_state(int index, Cloth *cloth, float *data) -{ - ClothVertex *vert = cloth->verts + index; - - memcpy(vert->x, data, 3 * sizeof(float)); - memcpy(vert->xconst, data + 3, 3 * sizeof(float)); - memcpy(vert->v, data + 6, 3 * sizeof(float)); -} -static void cloth_cache_interpolate(int index, Cloth *cloth, float frs_sec, float cfra, float cfra1, float cfra2, float *data1, float *data2) -{ - ClothVertex *vert = cloth->verts + index; - ParticleKey keys[4]; - float dfra; - - if(cfra1 == cfra2) { - cloth_read_state(index, cloth, data1); - return; - } - - memcpy(keys[1].co, data1, 3 * sizeof(float)); - memcpy(keys[1].vel, data1 + 6, 3 * sizeof(float)); - - memcpy(keys[2].co, data2, 3 * sizeof(float)); - memcpy(keys[2].vel, data2 + 6, 3 * sizeof(float)); - - dfra = cfra2 - cfra1; - - VecMulf(keys[1].vel, dfra); - VecMulf(keys[2].vel, dfra); - psys_interpolate_particle(-1, keys, (cfra - cfra1) / dfra, keys, 1); - - VecMulf(keys->vel, 1.0f / dfra); - - memcpy(vert->x, keys->co, 3 * sizeof(float)); - memcpy(vert->v, keys->vel, 3 * sizeof(float)); - - /* not sure what to do with this - jahka */ - memcpy(vert->xconst, data1 + 3, 3 * sizeof(float)); -} -void cloth_write_cache(Object *ob, ClothModifierData *clmd, int cfra) +int cloth_read_cache(Object *ob, ClothModifierData *clmd, float framenr) { - PTCacheWriter writer; PTCacheID pid; - + PTCacheFile *pf; + Cloth *cloth = clmd->clothObject; + unsigned int a, ret = 1; + + if(!cloth) + return 0; + BKE_ptcache_id_from_cloth(&pid, ob, clmd); - - writer.calldata = clmd->clothObject; - writer.cfra = cfra; - writer.set_elem = cloth_write_state; - writer.pid = &pid; - writer.totelem = clmd->clothObject->numverts; - - BKE_ptcache_write_cache(&writer); + pf = BKE_ptcache_file_open(&pid, PTCACHE_FILE_READ, framenr); + if(pf) { + for(a = 0; a < cloth->numverts; a++) { + if(!BKE_ptcache_file_read_floats(pf, cloth->verts[a].x, 3)) { + ret = 0; + break; + } + if(!BKE_ptcache_file_read_floats(pf, cloth->verts[a].xconst, 3)) { + ret = 0; + break; + } + if(!BKE_ptcache_file_read_floats(pf, cloth->verts[a].v, 3)) { + ret = 0; + break; + } + } + + BKE_ptcache_file_close(pf); + } + else + ret = 0; + + return ret; } -int cloth_read_cache(Scene *scene, Object *ob, ClothModifierData *clmd, float cfra, int *old_framenr) +void cloth_clear_cache(Object *ob, ClothModifierData *clmd, float framenr) { - PTCacheReader reader; PTCacheID pid; BKE_ptcache_id_from_cloth(&pid, ob, clmd); - reader.calldata = clmd->clothObject; - reader.cfra = cfra; - reader.interpolate_elem = cloth_cache_interpolate; - reader.old_frame = old_framenr; - reader.pid = &pid; - reader.scene = scene; - reader.set_elem = cloth_read_state; - reader.totelem = clmd->clothObject->numverts; - - return BKE_ptcache_read_cache(&reader); + // don't do anything as long as we're in editmode! + if(pid.cache->flag & PTCACHE_BAKE_EDIT_ACTIVE) + return; + + BKE_ptcache_id_clear(&pid, PTCACHE_CLEAR_AFTER, framenr); } -void cloth_clear_cache(Object *ob, ClothModifierData *clmd, float framenr) + +void cloth_write_cache(Object *ob, ClothModifierData *clmd, float framenr) { + Cloth *cloth = clmd->clothObject; PTCacheID pid; + PTCacheFile *pf; + unsigned int a; + + if(!cloth) + return; BKE_ptcache_id_from_cloth(&pid, ob, clmd); - - // don't do anything as long as we're in editmode! - if(pid.cache->flag & PTCACHE_BAKE_EDIT_ACTIVE) + pf = BKE_ptcache_file_open(&pid, PTCACHE_FILE_WRITE, framenr); + if(!pf) return; - BKE_ptcache_id_clear(&pid, PTCACHE_CLEAR_AFTER, framenr); + for(a = 0; a < cloth->numverts; a++) { + BKE_ptcache_file_write_floats(pf, cloth->verts[a].x, 3); + BKE_ptcache_file_write_floats(pf, cloth->verts[a].xconst, 3); + BKE_ptcache_file_write_floats(pf, cloth->verts[a].v, 3); + } + + BKE_ptcache_file_close(pf); } static int do_init_cloth(Object *ob, ClothModifierData *clmd, DerivedMesh *result, int framenr) @@ -509,7 +486,6 @@ DerivedMesh *clothModifier_do(ClothModifierData *clmd, Scene *scene, Object *ob, PTCacheID pid; float timescale; int framedelta, framenr, startframe, endframe; - int cache_result, old_framenr; clmd->scene= scene; /* nice to pass on later :) */ framenr= (int)scene->r.cfra; @@ -523,7 +499,6 @@ DerivedMesh *clothModifier_do(ClothModifierData *clmd, Scene *scene, Object *ob, if(!result) { cache->flag &= ~PTCACHE_SIMULATION_VALID; cache->simframe= 0; - cache->last_exact= 0; return dm; } @@ -535,7 +510,6 @@ DerivedMesh *clothModifier_do(ClothModifierData *clmd, Scene *scene, Object *ob, if(result->getNumVerts(result) != clmd->clothObject->numverts) { cache->flag &= ~PTCACHE_SIMULATION_VALID; cache->simframe= 0; - cache->last_exact= 0; return result; } } @@ -547,7 +521,6 @@ DerivedMesh *clothModifier_do(ClothModifierData *clmd, Scene *scene, Object *ob, if(BKE_ptcache_get_continue_physics()) { cache->flag &= ~PTCACHE_SIMULATION_VALID; cache->simframe= 0; - cache->last_exact= 0; /* do simulation */ if(!do_init_cloth(ob, clmd, result, framenr)) @@ -563,7 +536,6 @@ DerivedMesh *clothModifier_do(ClothModifierData *clmd, Scene *scene, Object *ob, if(framenr < startframe) { cache->flag &= ~PTCACHE_SIMULATION_VALID; cache->simframe= 0; - cache->last_exact= 0; return result; } else if(framenr > endframe) { @@ -580,9 +552,7 @@ DerivedMesh *clothModifier_do(ClothModifierData *clmd, Scene *scene, Object *ob, return result; /* try to read from cache */ - cache_result = cloth_read_cache(scene, ob, clmd, framenr, &old_framenr); - - if(cache_result == PTCACHE_READ_EXACT || cache_result == PTCACHE_READ_INTERPOLATED) { + if(cloth_read_cache(ob, clmd, framenr)) { cache->flag |= PTCACHE_SIMULATION_VALID; cache->simframe= framenr; @@ -591,40 +561,25 @@ DerivedMesh *clothModifier_do(ClothModifierData *clmd, Scene *scene, Object *ob, return result; } - else if(cache_result==PTCACHE_READ_OLD) { - BKE_ptcache_id_reset(scene, &pid, PTCACHE_RESET_FREE); - - implicit_set_positions(clmd); - - cache->flag |= PTCACHE_SIMULATION_VALID; - cache->simframe= old_framenr; - } else if(ob->id.lib || (cache->flag & PTCACHE_BAKED)) { /* if baked and nothing in cache, do nothing */ cache->flag &= ~PTCACHE_SIMULATION_VALID; cache->simframe= 0; - cache->last_exact= 0; return result; } if(framenr == startframe) { - if(cache->flag & PTCACHE_REDO_NEEDED) { - BKE_ptcache_id_reset(scene, &pid, PTCACHE_RESET_OUTDATED); - do_init_cloth(ob, clmd, result, framenr); - } cache->flag |= PTCACHE_SIMULATION_VALID; cache->simframe= framenr; /* don't write cache on first frame, but on second frame write * cache for frame 1 and 2 */ } - else { + else if(framedelta == 1) { /* if on second frame, write cache for first frame */ - if(cache->simframe == startframe && (cache->flag & PTCACHE_OUTDATED || cache->last_exact==0)) + if(framenr == startframe+1) cloth_write_cache(ob, clmd, startframe); - clmd->sim_parms->timescale *= framenr - cache->simframe; - /* do simulation */ cache->flag |= PTCACHE_SIMULATION_VALID; cache->simframe= framenr; @@ -632,13 +587,16 @@ DerivedMesh *clothModifier_do(ClothModifierData *clmd, Scene *scene, Object *ob, if(!do_step_cloth(ob, clmd, result, framenr)) { cache->flag &= ~PTCACHE_SIMULATION_VALID; cache->simframe= 0; - cache->last_exact= 0; } else cloth_write_cache(ob, clmd, framenr); cloth_to_object (ob, clmd, result); } + else { + cache->flag &= ~PTCACHE_SIMULATION_VALID; + cache->simframe= 0; + } return result; } diff --git a/source/blender/blenkernel/intern/constraint.c b/source/blender/blenkernel/intern/constraint.c index 88e73a00ba7..a43389a2ef6 100644 --- a/source/blender/blenkernel/intern/constraint.c +++ b/source/blender/blenkernel/intern/constraint.c @@ -3028,7 +3028,7 @@ static void transform_evaluate (bConstraint *con, bConstraintOb *cob, ListBase * if (VALID_CONS_TARGET(ct)) { float loc[3], eul[3], size[3]; float dvec[3], sval[3]; - int i; + short i; /* obtain target effect */ switch (data->from) { @@ -3075,7 +3075,7 @@ static void transform_evaluate (bConstraint *con, bConstraintOb *cob, ListBase * switch (data->to) { case 2: /* scaling */ for (i=0; i<3; i++) - size[i]= data->to_min[i] + (sval[(int)data->map[i]] * (data->to_max[i] - data->to_min[i])); + size[i]= data->to_min[i] + (sval[data->map[i]] * (data->to_max[i] - data->to_min[i])); break; case 1: /* rotation */ for (i=0; i<3; i++) { @@ -3085,7 +3085,7 @@ static void transform_evaluate (bConstraint *con, bConstraintOb *cob, ListBase * tmax= data->to_max[i]; /* all values here should be in degrees */ - eul[i]= tmin + (sval[(int)data->map[i]] * (tmax - tmin)); + eul[i]= tmin + (sval[data->map[i]] * (tmax - tmin)); /* now convert final value back to radians */ eul[i] = (float)(eul[i] / 180 * M_PI); @@ -3094,7 +3094,7 @@ static void transform_evaluate (bConstraint *con, bConstraintOb *cob, ListBase * default: /* location */ /* get new location */ for (i=0; i<3; i++) - loc[i]= (data->to_min[i] + (sval[(int)data->map[i]] * (data->to_max[i] - data->to_min[i]))); + loc[i]= (data->to_min[i] + (sval[data->map[i]] * (data->to_max[i] - data->to_min[i]))); /* add original location back on (so that it can still be moved) */ VecAddf(loc, cob->matrix[3], loc); diff --git a/source/blender/blenkernel/intern/context.c b/source/blender/blenkernel/intern/context.c index fbad585d9b7..6afbcf4950c 100644 --- a/source/blender/blenkernel/intern/context.c +++ b/source/blender/blenkernel/intern/context.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: context.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -358,9 +358,6 @@ static int ctx_data_collection_get(const bContext *C, const char *member, ListBa return 1; } - list->first= NULL; - list->last= NULL; - return 0; } @@ -368,20 +365,15 @@ PointerRNA CTX_data_pointer_get(const bContext *C, const char *member) { bContextDataResult result; - if(ctx_data_get((bContext*)C, member, &result)) + if(ctx_data_get((bContext*)C, member, &result)) { return result.ptr; - else - return PointerRNA_NULL; -} - -PointerRNA CTX_data_pointer_get_type(const bContext *C, const char *member, StructRNA *type) -{ - PointerRNA ptr = CTX_data_pointer_get(C, member); - - if(ptr.data && ptr.type == type) + } + else { + PointerRNA ptr; + memset(&ptr, 0, sizeof(ptr)); return ptr; - - return PointerRNA_NULL; + } + } ListBase CTX_data_collection_get(const bContext *C, const char *member) diff --git a/source/blender/blenkernel/intern/depsgraph.c b/source/blender/blenkernel/intern/depsgraph.c index a36b825293e..8bb34bde122 100644 --- a/source/blender/blenkernel/intern/depsgraph.c +++ b/source/blender/blenkernel/intern/depsgraph.c @@ -559,7 +559,7 @@ static void build_dag_object(DagForest *dag, DagNode *scenenode, Scene *scene, O dag_add_relation(dag, node, node, DAG_RL_OB_DATA, "Particle-Object Relation"); - if(!psys_check_enabled(ob, psys)) + if(psys->flag & PSYS_DISABLED || psys->flag & PSYS_DELETE) continue; if(part->phystype==PART_PHYS_KEYED && psys->keyed_ob && @@ -1831,7 +1831,7 @@ static unsigned int flush_layer_node(Scene *sce, DagNode *node, int curtime) } /* node was checked to have lasttime != curtime , and is of type ID_OB */ -static void flush_pointcache_reset(Scene *scene, DagNode *node, int curtime, int reset) +static void flush_pointcache_reset(DagNode *node, int curtime, int reset) { DagAdjList *itA; Object *ob; @@ -1844,13 +1844,13 @@ static void flush_pointcache_reset(Scene *scene, DagNode *node, int curtime, int ob= (Object*)(node->ob); if(reset || (ob->recalc & OB_RECALC)) { - if(BKE_ptcache_object_reset(scene, ob, PTCACHE_RESET_DEPSGRAPH)) + if(BKE_ptcache_object_reset(ob, PTCACHE_RESET_DEPSGRAPH)) ob->recalc |= OB_RECALC_DATA; - flush_pointcache_reset(scene, itA->node, curtime, 1); + flush_pointcache_reset(itA->node, curtime, 1); } else - flush_pointcache_reset(scene, itA->node, curtime, 0); + flush_pointcache_reset(itA->node, curtime, 0); } } } @@ -1908,13 +1908,13 @@ void DAG_scene_flush_update(Scene *sce, unsigned int lay, int time) ob= (Object*)(itA->node->ob); if(ob->recalc & OB_RECALC) { - if(BKE_ptcache_object_reset(sce, ob, PTCACHE_RESET_DEPSGRAPH)) + if(BKE_ptcache_object_reset(ob, PTCACHE_RESET_DEPSGRAPH)) ob->recalc |= OB_RECALC_DATA; - flush_pointcache_reset(sce, itA->node, lasttime, 1); + flush_pointcache_reset(itA->node, lasttime, 1); } else - flush_pointcache_reset(sce, itA->node, lasttime, 0); + flush_pointcache_reset(itA->node, lasttime, 0); } } } @@ -2132,7 +2132,7 @@ void DAG_object_flush_update(Scene *sce, Object *ob, short flag) if(ob==NULL || sce->theDag==NULL) return; ob->recalc |= flag; - BKE_ptcache_object_reset(sce, ob, PTCACHE_RESET_DEPSGRAPH); + BKE_ptcache_object_reset(ob, PTCACHE_RESET_DEPSGRAPH); /* all users of this ob->data should be checked */ /* BUT! displists for curves are still only on cu */ @@ -2147,7 +2147,7 @@ void DAG_object_flush_update(Scene *sce, Object *ob, short flag) for (obt=G.main->object.first; obt; obt= obt->id.next) { if (obt != ob && obt->data==ob->data) { obt->recalc |= OB_RECALC_DATA; - BKE_ptcache_object_reset(sce, obt, PTCACHE_RESET_DEPSGRAPH); + BKE_ptcache_object_reset(obt, PTCACHE_RESET_DEPSGRAPH); } } } diff --git a/source/blender/blenkernel/intern/displist.c b/source/blender/blenkernel/intern/displist.c index cdf4b90cee1..736165a8a98 100644 --- a/source/blender/blenkernel/intern/displist.c +++ b/source/blender/blenkernel/intern/displist.c @@ -315,19 +315,13 @@ static void init_fastshade_shadeinput(Render *re) static Render *fastshade_get_render(Scene *scene) { - /* XXX ugly global still, but we can't do preview while rendering */ - if(G.rendering==0) { - - Render *re= RE_GetRender("_Shade View_"); - if(re==NULL) { - re= RE_NewRender("_Shade View_"); - - RE_Database_Baking(re, scene, 0, 0); /* 0= no faces */ - } - return re; - } + Render *re= RE_GetRender("_Shade View_"); + if(re==NULL) { + re= RE_NewRender("_Shade View_"); - return NULL; + RE_Database_Baking(re, scene, 0, 0); /* 0= no faces */ + } + return re; } /* called on file reading */ @@ -617,20 +611,18 @@ static void mesh_create_shadedColors(Render *re, Object *ob, int onlyForMesh, un void shadeMeshMCol(Scene *scene, Object *ob, Mesh *me) { - Render *re= fastshade_get_render(scene); int a; char *cp; unsigned int *mcol= (unsigned int*)me->mcol; - if(re) { - mesh_create_shadedColors(re, ob, 1, &mcol, NULL); - me->mcol= (MCol*)mcol; + Render *re= fastshade_get_render(scene); + mesh_create_shadedColors(re, ob, 1, &mcol, NULL); + me->mcol= (MCol*)mcol; - /* swap bytes */ - for(cp= (char *)me->mcol, a= 4*me->totface; a>0; a--, cp+=4) { - SWAP(char, cp[0], cp[3]); - SWAP(char, cp[1], cp[2]); - } + /* swap bytes */ + for(cp= (char *)me->mcol, a= 4*me->totface; a>0; a--, cp+=4) { + SWAP(char, cp[0], cp[3]); + SWAP(char, cp[1], cp[2]); } } @@ -649,8 +641,6 @@ void shadeDispList(Scene *scene, Base *base) int a, need_orco; re= fastshade_get_render(scene); - if(re==NULL) - return; dl = find_displist(&ob->disp, DL_VERTCOL); if (dl) { diff --git a/source/blender/blenkernel/intern/effect.c b/source/blender/blenkernel/intern/effect.c index eaa2d541638..9858025af5a 100644 --- a/source/blender/blenkernel/intern/effect.c +++ b/source/blender/blenkernel/intern/effect.c @@ -29,8 +29,6 @@ * ***** END GPL LICENSE BLOCK ***** */ -#include "BLI_storage.h" /* _LARGEFILE_SOURCE */ - #include <math.h> #include <stdlib.h> diff --git a/source/blender/blenkernel/intern/exotic.c b/source/blender/blenkernel/intern/exotic.c index 4e7e76dfae3..929d3f942dc 100644 --- a/source/blender/blenkernel/intern/exotic.c +++ b/source/blender/blenkernel/intern/exotic.c @@ -27,9 +27,48 @@ * * - Blender Foundation * - * ***** END GPL LICENSE BLOCK *****/ + * ***** END GPL LICENSE BLOCK ***** + * + * eigen videoscape formaat: + * + * + * lamp: + * 3DG2 + aantal_lampen + + type + spsi spbl + r, g, b, energy + locx, locy, locz + vecx, vecy, vecz + + + curve / nurbs: + 3DG3 + 5 of 11 (curve of surf) + aantal_nurbs + extr1 extr2 + + mat[0][0] mat[0][1] mat[0][2] mat[0][3] + mat[1][0] mat[1][1] mat[1][2] mat[1][3] + ... + + type + pntsu, pntsv + resolu, resolv + orderu, orderv + flagu, flagv + + (als type==nurb) x y z w + x y z w + ... + (als type==bez) xyz xyz xyz h1 h2 h3 + xyz xyz xyz h1 h2 h3 + ... + * + * + */ -#include "BLI_storage.h" #include <ctype.h> /* isdigit, isspace */ #include <math.h> @@ -443,6 +482,385 @@ static void read_stl_mesh_ascii(Scene *scene, char *str) #undef STLREADLINE #undef STLREADVERT +static void read_videoscape_mesh(Scene *scene, char *str) +{ + Object *ob; + Mesh *me; + MVert *mvert; + MFace *mface; + Material *ma; + FILE *fp; + float *vertdata, *vd, min[3], max[3], cent[3], ftemp; + unsigned int color[32], col; + int totcol, a, b, verts, tottria=0, totquad=0, totedge=0, poly, nr0, nr, first; + int end; + char s[50]; + + fp= fopen(str, "rb"); + if(fp==NULL) { + //XXX error("Can't read file"); + return; + } + + fscanf(fp, "%40s", s); + + fscanf(fp, "%d\n", &verts); + if(verts<=0) { + fclose(fp); + //XXX error("Read error"); + return; + } + + if(verts>MESH_MAX_VERTS) { + //XXX error("too many vertices"); + fclose(fp); + return; + } + + INIT_MINMAX(min, max); + vd= vertdata= MEM_mallocN(sizeof(float)*3*verts, "videoscapelezer"); + + for(a=0; a<verts; a++) { + fscanf(fp, "%f %f %f", vd, vd+1, vd+2); + DO_MINMAX(vd, min, max); + vd+=3; + } + + /* count faces and colors */ + for(a=0; a<32; a++) color[a]= 0; + totcol= 0; + end= 1; + while(end>0) { + end= fscanf(fp,"%d", &poly); + if(end<=0) break; + + if(poly==3) tottria++; + else if(poly==4) totquad++; + else totedge+= poly; + + for(a=0;a<poly;a++) { + end= fscanf(fp,"%d", &nr); + if(end<=0) break; + } + if(end<=0) break; + + end= fscanf(fp,"%i\n", &col); + col &= 0xF0F0F0; + for(a=0; a<totcol; a++) { + if(color[a]==col) break; + } + if(a>=totcol && totcol<32) { + color[totcol]= col; + totcol++; + } + } + + /* new object */ + ob= add_object(scene, OB_MESH); + me= ob->data; + me->totvert= verts; + me->totface= totedge+tottria+totquad; + + me->mvert= CustomData_add_layer(&me->vdata, CD_MVERT, CD_CALLOC, + NULL, me->totvert); + me->mface= CustomData_add_layer(&me->fdata, CD_MFACE, CD_CALLOC, + NULL, me->totface); + + /* colors */ + if(totcol) { + ob->mat= MEM_callocN(sizeof(void *)*totcol, "ob->mat"); + me->mat= MEM_callocN(sizeof(void *)*totcol, "me->mat"); + me->totcol= totcol; + ob->totcol= (unsigned char) me->totcol; + ob->actcol= 1; + } + + /* materials */ + for(a=0; a<totcol; a++) { + ma= G.main->mat.first; + while(ma) { + if(ma->mtex[0]==0) { + col= rgb_to_cpack(ma->r, ma->g, ma->b); + if(color[a]==col) { + me->mat[a]= ma; + ma->id.us++; + break; + } + } + ma= ma->id.next; + } + if(ma==0) { + ma= add_material("ext"); + me->mat[a]= ma; + cpack_to_rgb(color[a], cent, cent+1, cent+2); + ma->r= cent[0]; + ma->g= cent[1]; + ma->b= cent[2]; + automatname(ma); + } + } + + /* verts */ + + cent[0]= (min[0]+max[0])/2.0f; + cent[1]= (min[1]+max[1])/2.0f; + cent[2]= (min[2]+max[2])/2.0f; + VECCOPY(ob->loc, cent); + + a= me->totvert; + vd= vertdata; + mvert= me->mvert; + while(a--) { + VecSubf(mvert->co, vd, cent); + mvert++; + vd+= 3; + } + + /* faces */ + if(me->totface) { + rewind(fp); + + fscanf(fp, "%40s", s); + fscanf(fp, "%d\n", &verts); + /* fake read */ + for(a=0;a<verts;a++) { + fscanf(fp, "%f %f %f", &ftemp, &ftemp, &ftemp); + } + + a= me->totface; + mface= me->mface; + while(a--) { + end= fscanf(fp,"%d", &poly); + if(end<=0) break; + + if(poly==3 || poly==4) { + fscanf(fp,"%d", &nr); + mface->v1= MIN2(nr, me->totvert-1); + fscanf(fp,"%d", &nr); + mface->v2= MIN2(nr, me->totvert-1); + fscanf(fp,"%d", &nr); + mface->v3= MIN2(nr, me->totvert-1); + if(poly==4) { + if( fscanf(fp,"%d", &nr) <=0 ) break; + mface->v4= MIN2(nr, me->totvert-1); + } + + test_index_face(mface, NULL, 0, poly); + + mface++; + } + else { + if( fscanf(fp,"%d", &nr0) <=0) break; + first= nr0; + for(b=1; b<poly; b++) { + end= fscanf(fp,"%d", &nr); + if(end<=0) break; + nr= MIN2(nr, me->totvert-1); + mface->v1= nr; + mface->v2= nr0; + nr0= nr; + mface++; + a--; + } + mface->v1= first; + mface->v2= nr; + mface++; + if(end<=0) break; + } + end= fscanf(fp,"%i", &col); + col &= 0xF0F0F0; + if(end<=0) break; + + for(b=0; b<totcol; b++) { + if(color[b]==col) { + (mface-1)->mat_nr= b; + break; + } + } + } + } + + fclose(fp); + MEM_freeN(vertdata); + + mesh_add_normals_flags(me); + make_edges(me, 0); + + //XXX waitcursor(1); +} + +static void read_videoscape_lamp(Scene *scene, char *str) +{ + Object *ob; + Lamp *la; + FILE *fp; + float vec[3], q1[4]; + int tot, val; + char s[50]; + + fp= fopen(str, "rb"); + if(fp==NULL) { + //XXX error("Can't read file"); + return; + } + + fscanf(fp, "%40s", s); + fscanf(fp, "%d\n", &tot); + + while(tot--) { + ob= add_object(scene, OB_LAMP); + la= ob->data; + + fscanf(fp, "%d\n", &val); + la->type= val; + if(la->type==1) la->type= LA_SPOT; + else if(la->type==2) la->type= LA_SUN; + + fscanf(fp, "%f %f\n", &la->spotsize, &la->spotblend); + + fscanf(fp, "%f %f %f %f\n", &la->r, &la->g, &la->b, &la->energy); + + fscanf(fp, "%f %f %f\n", ob->loc, ob->loc+1, ob->loc+2); + val= fscanf(fp, "%f %f %f\n", vec, vec+1, vec+2); + vectoquat(vec, 5, 2, q1); + QuatToEul(q1, ob->rot); + + if(val<=0) break; + + } + fclose(fp); +} + +static void read_videoscape_nurbs(Scene *scene, char *str) +{ + Object *ob; + Curve *cu; + Nurb *nu; + BezTriple *bezt; + BPoint *bp; + FILE *fp; + float tmat[4][4], omat[3][3], imat[3][3], mat[3][3]; + int a, tot, type, val; + char s[50]; + + fp= fopen(str, "rb"); + if(fp==NULL) { + //XXX error("Can't read file"); + return; + } + + fscanf(fp, "%40s", s); + fscanf(fp, "%d\n", &type); + + if(type==5) ob= add_object(scene, OB_SURF); + else ob= add_object(scene, OB_CURVE); + cu= ob->data; + + fscanf(fp, "%d\n", &tot); + fscanf(fp, "%d %d\n", &type, &val); + + cu->ext1= 0.002f*type; + cu->ext2= 0.002f*val; + + for(a=0; a<4; a++) fscanf(fp, "%e %e %e %e\n", tmat[a], tmat[a]+1, tmat[a]+2, tmat[a]+3); + + VECCOPY(ob->loc, tmat[3]); + + Mat3CpyMat4(omat, tmat); + Mat3ToEul(omat, ob->rot); + EulToMat3(ob->rot, mat); + Mat3Inv(imat, mat); + Mat3MulMat3((float ( * )[3])tmat, imat, omat); + + while(tot--) { + nu= (Nurb*)MEM_callocN(sizeof(Nurb),"nu from exotic"); + BLI_addtail(&cu->nurb, nu); + + fscanf(fp, "%d\n", &type); + nu->type= type; + + fscanf(fp, "%d %d\n", &type, &val); + nu->pntsu= type; nu->pntsv= val; + fscanf(fp, "%d %d\n", &type, &val); + nu->resolu= type; nu->resolv= val; + fscanf(fp, "%d %d\n", &type, &val); + nu->orderu= type; nu->orderv= val; + fscanf(fp, "%d %d\n", &type, &val); + nu->flagu= type; nu->flagv= val; + + if( (nu->type & 7)==CU_BEZIER) { + a= nu->pntsu; + nu->bezt= bezt= MEM_callocN(a*sizeof(BezTriple), "bezt from exotic"); + while(a--) { + fscanf(fp, "%f %f %f ", bezt->vec[0], bezt->vec[0]+1, bezt->vec[0]+2); + Mat4MulVecfl(tmat, bezt->vec[0]); + fscanf(fp, "%f %f %f ", bezt->vec[1], bezt->vec[1]+1, bezt->vec[1]+2); + Mat4MulVecfl(tmat, bezt->vec[1]); + fscanf(fp, "%f %f %f ", bezt->vec[2], bezt->vec[2]+1, bezt->vec[2]+2); + Mat4MulVecfl(tmat, bezt->vec[2]); + fscanf(fp, "%d %d\n", &type, &val); + bezt->h1= type; + bezt->h2= val; + bezt++; + } + } + else { + a= nu->pntsu*nu->pntsv; + if(a) { + nu->bp= bp= MEM_callocN(a*sizeof(BPoint), "bp from exotic"); + while(a--) { + fscanf(fp, "%f %f %f %f\n", bp->vec, bp->vec+1, bp->vec+2, bp->vec+3); + Mat4MulVecfl(tmat, bp->vec); + bp++; + } + + val= KNOTSU(nu); + nu->knotsu= MEM_mallocN(sizeof(float)*val, "knots"); + for(a=0; a<val; a++) fscanf(fp, "%f\n", nu->knotsu+a); + + if(nu->pntsv>1) { + val= KNOTSV(nu); + nu->knotsv= MEM_mallocN(sizeof(float)*val, "knots"); + for(a=0; a<val; a++) fscanf(fp, "%f\n", nu->knotsv+a); + } + } + else { + BLI_remlink(&cu->nurb, nu); + MEM_freeN(nu); + } + } + } + fclose(fp); +} + +static void read_videoscape(Scene *scene, char *str) +{ + int file, type; + unsigned int val; + unsigned short numlen; + char name[FILE_MAXDIR+FILE_MAXFILE], head[FILE_MAXDIR+FILE_MAXFILE], tail[FILE_MAXFILE]; + + strcpy(name, str); + + while( TRUE ) { + file= open(name, O_BINARY|O_RDONLY); + if(file<=0) break; + else { + read(file, &type, 4); + close(file); + + if(type==DDG1) read_videoscape_mesh(scene, name); + else if(type==DDG2) read_videoscape_lamp(scene, name); + else if(type==DDG3) read_videoscape_nurbs(scene, name); + } + + val = BLI_stringdec(name, head, tail, &numlen); + BLI_stringenc(name, head, tail, numlen, val + 1); + + } +} + + /* ***************** INVENTOR ******************* */ @@ -1786,7 +2204,16 @@ int BKE_read_exotic(Scene *scene, char *name) if ((*s0 != FORM) && (strncmp(str, "BLEN", 4) != 0) && !BLI_testextensie(name,".blend.gz")) { //XXX waitcursor(1); - if(strncmp(str, "#Inventor V1.0", 14)==0) { + + if(ELEM4(*s0, DDG1, DDG2, DDG3, DDG4)) { + if(0) { // XXX obedit) { + //XXX error("Unable to perform function in EditMode"); + } else { + read_videoscape(scene, name); + retval = 1; + } + } + else if(strncmp(str, "#Inventor V1.0", 14)==0) { if( strncmp(str+15, "ascii", 5)==0) { read_inventor(scene, name, &lbase); displist_to_objects(scene, &lbase); @@ -1958,6 +2385,167 @@ void write_stl(Scene *scene, char *str) //XXX waitcursor(0); } +static void write_videoscape_mesh(Scene *scene, Object *ob, char *str) +{ + Mesh *me= ob->data; + EditMesh *em = BKE_mesh_get_editmesh(me); + Material *ma; + MFace *mface; + FILE *fp; + EditVert *eve; + EditFace *evl; + unsigned int kleur[32]; + float co[3]; + int a; + intptr_t tot; + char *cp; + + if(ob && ob->type==OB_MESH); + else { + return; + } + + kleur[0]= 0x00C0C0C0; + + cp= (char *)kleur; + for(a=0; a<ob->totcol; a++, cp+=4) { + + ma= give_current_material(ob, a+1); + if(ma) { + cp[0]= (unsigned char) (255.0*ma->emit); + cp[1]= (unsigned char) (255.0*ma->b); + cp[2]= (unsigned char) (255.0*ma->g); + cp[3]= (unsigned char) (255.0*ma->r); + if(ENDIAN_ORDER==L_ENDIAN) SWITCH_INT(kleur[a]); + } + else kleur[a]= 0x00C0C0C0; + + if(a>30) break; + } + + fp= fopen(str, "wb"); + if(fp==NULL) return; + + fprintf(fp,"3DG1\n"); + + if(em) { + + fprintf(fp, "%d\n", em->totvert); + + tot= 0; + eve= em->verts.first; + while(eve) { + VECCOPY(co, eve->co); + Mat4MulVecfl(ob->obmat, co); + fprintf(fp, "%f %f %f\n", co[0], co[1], co[2] ); + eve->tmp.l = tot; + tot++; + eve= eve->next; + } + evl= em->faces.first; + while(evl) { + + if(evl->v4==0) { + fprintf(fp, "3 %ld %ld %ld 0x%x\n", + (intptr_t) evl->v1->tmp.l, + (intptr_t) evl->v2->tmp.l, + (intptr_t) evl->v3->tmp.l, + kleur[evl->mat_nr]); + } + else { + fprintf(fp, "4 %ld %ld %ld %ld 0x%x\n", + (intptr_t) evl->v1->tmp.l, + (intptr_t) evl->v2->tmp.l, + (intptr_t) evl->v3->tmp.l, + (intptr_t) evl->v4->tmp.l, + kleur[evl->mat_nr]); + } + evl= evl->next; + } + } + else { + DerivedMesh *dm = mesh_get_derived_deform(scene, ob, CD_MASK_BAREMESH); + + me= ob->data; + + fprintf(fp, "%d\n", me->totvert); + + mface= me->mface; + for(a=0; a<me->totvert; a++) { + dm->getVertCo(dm, a, co); + Mat4MulVecfl(ob->obmat, co); + fprintf(fp, "%f %f %f\n", co[0], co[1], co[2] ); + } + for(a=0; a<me->totface; a++, mface++) { + if(mface->v4==0) { + fprintf(fp, "3 %d %d %d 0x%x\n", mface->v1, mface->v2, mface->v3, kleur[(int)mface->mat_nr]); + } + else { + fprintf(fp, "4 %d %d %d %d 0x%x\n", mface->v1, mface->v2, mface->v3, mface->v4, kleur[(int)mface->mat_nr]); + } + } + + dm->release(dm); + } + + fclose(fp); + + if (em) BKE_mesh_end_editmesh(me, em); + +} + + +void write_videoscape(Scene *scene, char *str) +{ + Base *base; + int file, val, lampdone=0; + unsigned short numlen; + char head[FILE_MAXFILE], tail[FILE_MAXFILE]; + + if(BLI_testextensie(str,".trace")) str[ strlen(str)-6]= 0; + if(BLI_testextensie(str,".blend")) str[ strlen(str)-6]= 0; + if(BLI_testextensie(str,".ble")) str[ strlen(str)-4]= 0; + if(BLI_testextensie(str,".obj")==0) strcat(str, ".obj"); + + file= open(str,O_BINARY|O_RDONLY); + close(file); + //XXX saveover() + // if(file>-1) if(!during_script() && saveover(str)==0) return; + + strcpy(temp_dir, str); + + base= scene->base.first; + while(base) { + if((base->flag & SELECT) && (base->lay & scene->lay)) { + if(base->object->type==OB_MESH) { + write_videoscape_mesh(scene, base->object, str); + val = BLI_stringdec(str, head, tail, &numlen); + BLI_stringenc(str, head, tail, numlen, val + 1); + } + else if(base->object->type==OB_CURVE || base->object->type==OB_SURF) { + /* write_videoscape_nurbs(base->object, str); */ + /* val = stringdec(str, head, tail, &numlen); */ + /* stringenc(str, head, tail, numlen, val + 1); */ + } + else if(lampdone==0 && base->object->type==OB_LAMP) { + /* lampdone= 1; */ + /* write_videoscape_lamps(str); */ + /* val = stringdec(str, head, tail, &numlen); */ + /* stringenc(str, head, tail, numlen, val + 1); */ + } + } + base= base->next; + } + + + /* remove when higher numbers exist */ + while(remove(str)==0) { + + val = BLI_stringdec(str, head, tail, &numlen); + BLI_stringenc(str, head, tail, numlen, val + 1); + } +} + /* ******************************* WRITE VRML ***************************** */ static void replace_chars(char *str1, char *str2) diff --git a/source/blender/blenkernel/intern/fluidsim.c b/source/blender/blenkernel/intern/fluidsim.c index 54008185f72..9eefd48cae4 100644 --- a/source/blender/blenkernel/intern/fluidsim.c +++ b/source/blender/blenkernel/intern/fluidsim.c @@ -28,8 +28,6 @@ * ***** END GPL LICENSE BLOCK ***** */ -#include "BLI_storage.h" /* _LARGEFILE_SOURCE */ - #include "MEM_guardedalloc.h" #include "DNA_mesh_types.h" diff --git a/source/blender/blenkernel/intern/gpencil.c b/source/blender/blenkernel/intern/gpencil.c index dd8f44c71d5..6086aa58d40 100644 --- a/source/blender/blenkernel/intern/gpencil.c +++ b/source/blender/blenkernel/intern/gpencil.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: gpencil.c 19758 2009-04-16 13:10:08Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenkernel/intern/idprop.c b/source/blender/blenkernel/intern/idprop.c index 54366aadd92..3be47778674 100644 --- a/source/blender/blenkernel/intern/idprop.c +++ b/source/blender/blenkernel/intern/idprop.c @@ -230,16 +230,16 @@ void IDP_ResizeArray(IDProperty *prop, int newlen) */ newsize = (newsize >> 3) + (newsize < 9 ? 3 : 6) + newsize; - newarr = MEM_callocN(idp_size_table[(int)prop->subtype]*newsize, "idproperty array resized"); + newarr = MEM_callocN(idp_size_table[prop->subtype]*newsize, "idproperty array resized"); if (newlen >= prop->len) { /* newlen is bigger*/ - memcpy(newarr, prop->data.pointer, prop->len*idp_size_table[(int)prop->subtype]); + memcpy(newarr, prop->data.pointer, prop->len*idp_size_table[prop->subtype]); idp_resize_group_array(prop, newlen, newarr); } else { /* newlen is smaller*/ idp_resize_group_array(prop, newlen, newarr); - memcpy(newarr, prop->data.pointer, newlen*prop->len*idp_size_table[(int)prop->subtype]); + memcpy(newarr, prop->data.pointer, newlen*prop->len*idp_size_table[prop->subtype]); } MEM_freeN(prop->data.pointer); @@ -546,7 +546,7 @@ int IDP_EqualsProperties(IDProperty *prop1, IDProperty *prop2) return BSTR_EQ(IDP_String(prop1), IDP_String(prop2)); else if(prop1->type == IDP_ARRAY) { if(prop1->len == prop2->len && prop1->subtype == prop2->subtype) - return memcmp(IDP_Array(prop1), IDP_Array(prop2), idp_size_table[(int)prop1->subtype]*prop1->len); + return memcmp(IDP_Array(prop1), IDP_Array(prop2), idp_size_table[prop1->subtype]*prop1->len); else return 0; } diff --git a/source/blender/blenkernel/intern/image.c b/source/blender/blenkernel/intern/image.c index 6b231cfc702..8eef9984c92 100644 --- a/source/blender/blenkernel/intern/image.c +++ b/source/blender/blenkernel/intern/image.c @@ -1812,7 +1812,7 @@ static ImBuf *image_get_render_result(Image *ima, ImageUser *iuser) Render *re= NULL; RenderResult *rr= NULL; - if(iuser && iuser->scene) { + if(iuser->scene) { re= RE_GetRender(iuser->scene->id.name); rr= RE_GetResult(re); } diff --git a/source/blender/blenkernel/intern/implicit.c b/source/blender/blenkernel/intern/implicit.c index fc5213d5532..40c98c1d9cc 100644 --- a/source/blender/blenkernel/intern/implicit.c +++ b/source/blender/blenkernel/intern/implicit.c @@ -1600,10 +1600,6 @@ int implicit_solver (Object *ob, float frame, ClothModifierData *clmd, ListBase if(clmd->coll_parms->flags & CLOTH_COLLSETTINGS_FLAG_ENABLED) { - float temp = clmd->sim_parms->stepsPerFrame; - /* not too nice hack, but collisions need this correction -jahka */ - clmd->sim_parms->stepsPerFrame /= clmd->sim_parms->timescale; - // collisions // itstart(); @@ -1618,7 +1614,7 @@ int implicit_solver (Object *ob, float frame, ClothModifierData *clmd, ListBase // call collision function // TODO: check if "step" or "step+dt" is correct - dg - result = cloth_bvh_objcollision(ob, clmd, step/clmd->sim_parms->timescale, dt/clmd->sim_parms->timescale); + result = cloth_bvh_objcollision(ob, clmd, step, dt); // correct velocity again, just to be sure we had to change it due to adaptive collisions for(i = 0; i < numverts; i++) @@ -1641,9 +1637,6 @@ int implicit_solver (Object *ob, float frame, ClothModifierData *clmd, ListBase } } - /* restore original stepsPerFrame */ - clmd->sim_parms->stepsPerFrame = temp; - // X = Xnew; cp_lfvector(id->X, id->Xnew, numverts); @@ -1661,6 +1654,7 @@ int implicit_solver (Object *ob, float frame, ClothModifierData *clmd, ListBase simulate_implicit_euler(id->Vnew, id->X, id->V, id->F, id->dFdV, id->dFdX, dt / 2.0f, id->A, id->B, id->dV, id->S, id->z, id->olddV, id->P, id->Pinv, id->M, id->bigI); } + } else { diff --git a/source/blender/blenkernel/intern/material.c b/source/blender/blenkernel/intern/material.c index 57b88bb0b3f..b410c521dea 100644 --- a/source/blender/blenkernel/intern/material.c +++ b/source/blender/blenkernel/intern/material.c @@ -615,7 +615,7 @@ int find_material_index(Object *ob, Material *ma) return 0; } -void object_add_material_slot(Object *ob) +void new_material_to_objectdata(Object *ob) { Material *ma; @@ -854,7 +854,7 @@ void automatname(Material *ma) } -void object_remove_material_slot(Object *ob) +void delete_material_index(Object *ob) { Material *mao, ***matarar; Object *obt; diff --git a/source/blender/blenkernel/intern/modifier.c b/source/blender/blenkernel/intern/modifier.c index 80a9f173d6a..bf3d27cafbf 100644 --- a/source/blender/blenkernel/intern/modifier.c +++ b/source/blender/blenkernel/intern/modifier.c @@ -3543,7 +3543,7 @@ static void displaceModifier_updateDepgraph( } } -static void validate_layer_name(const CustomData *data, int type, char *name, char *outname) +static void validate_layer_name(const CustomData *data, int type, char *name) { int index = -1; @@ -3556,10 +3556,8 @@ static void validate_layer_name(const CustomData *data, int type, char *name, ch * deleted, so assign the active layer to name */ index = CustomData_get_active_layer_index(data, CD_MTFACE); - strcpy(outname, data->layers[index].name); + strcpy(name, data->layers[index].name); } - else - strcpy(outname, name); } static void get_texture_coords(DisplaceModifierData *dmd, Object *ob, @@ -3585,11 +3583,12 @@ static void get_texture_coords(DisplaceModifierData *dmd, Object *ob, char *done = MEM_callocN(sizeof(*done) * numVerts, "get_texture_coords done"); int numFaces = dm->getNumFaces(dm); - char uvname[32]; MTFace *tf; - validate_layer_name(&dm->faceData, CD_MTFACE, dmd->uvlayer_name, uvname); - tf = CustomData_get_layer_named(&dm->faceData, CD_MTFACE, uvname); + validate_layer_name(&dm->faceData, CD_MTFACE, dmd->uvlayer_name); + + tf = CustomData_get_layer_named(&dm->faceData, CD_MTFACE, + dmd->uvlayer_name); /* verts are given the UV from the first face that uses them */ for(i = 0, mf = mface; i < numFaces; ++i, ++mf, ++tf) { @@ -3885,7 +3884,6 @@ static DerivedMesh *uvprojectModifier_do(UVProjectModifierData *umd, Projector projectors[MOD_UVPROJECT_MAXPROJECTORS]; int num_projectors = 0; float aspect; - char uvname[32]; if(umd->aspecty != 0) aspect = umd->aspectx / umd->aspecty; else aspect = 1.0f; @@ -3900,11 +3898,12 @@ static DerivedMesh *uvprojectModifier_do(UVProjectModifierData *umd, if(!dm->getFaceDataArray(dm, CD_MTFACE)) return dm; /* make sure we're using an existing layer */ - validate_layer_name(&dm->faceData, CD_MTFACE, umd->uvlayer_name, uvname); + validate_layer_name(&dm->faceData, CD_MTFACE, umd->uvlayer_name); /* make sure we are not modifying the original UV layer */ tface = CustomData_duplicate_referenced_layer_named(&dm->faceData, - CD_MTFACE, uvname); + CD_MTFACE, + umd->uvlayer_name); numVerts = dm->getNumVerts(dm); @@ -5186,11 +5185,12 @@ static void wavemod_get_texture_coords(WaveModifierData *wmd, Object *ob, char *done = MEM_callocN(sizeof(*done) * numVerts, "get_texture_coords done"); int numFaces = dm->getNumFaces(dm); - char uvname[32]; MTFace *tf; - validate_layer_name(&dm->faceData, CD_MTFACE, wmd->uvlayer_name, uvname); - tf = CustomData_get_layer_named(&dm->faceData, CD_MTFACE, uvname); + validate_layer_name(&dm->faceData, CD_MTFACE, wmd->uvlayer_name); + + tf = CustomData_get_layer_named(&dm->faceData, CD_MTFACE, + wmd->uvlayer_name); /* verts are given the UV from the first face that uses them */ for(i = 0, mf = mface; i < numFaces; ++i, ++mf, ++tf) { @@ -6295,9 +6295,6 @@ CustomDataMask particleSystemModifier_requiredDataMask(Object *ob, ModifierData MTex *mtex; int i; - if(!psmd->psys->part) - return 0; - ma= give_current_material(ob, psmd->psys->part->omat); if(ma) { for(i=0; i<MAX_MTEX; i++) { diff --git a/source/blender/blenkernel/intern/multires.c b/source/blender/blenkernel/intern/multires.c index 5def910ddef..b1387281cf5 100644 --- a/source/blender/blenkernel/intern/multires.c +++ b/source/blender/blenkernel/intern/multires.c @@ -1270,10 +1270,8 @@ void multires_free(Multires *mr) if(lvl) { CustomData_free(&mr->vdata, lvl->totvert); CustomData_free(&mr->fdata, lvl->totface); - if(mr->edge_flags) - MEM_freeN(mr->edge_flags); - if(mr->edge_creases) - MEM_freeN(mr->edge_creases); + MEM_freeN(mr->edge_flags); + MEM_freeN(mr->edge_creases); } while(lvl) { diff --git a/source/blender/blenkernel/intern/particle.c b/source/blender/blenkernel/intern/particle.c index 2474053298d..34e69b2d736 100644 --- a/source/blender/blenkernel/intern/particle.c +++ b/source/blender/blenkernel/intern/particle.c @@ -222,34 +222,6 @@ short psys_get_current_num(Object *ob) return i; } -void psys_set_current_num(Object *ob, int index) -{ - ParticleSystem *psys; - short i; - - if(ob==0) return; - - for(psys=ob->particlesystem.first, i=0; psys; psys=psys->next, i++) { - if(i == index - 1) - psys->flag |= PSYS_CURRENT; - else - psys->flag &= ~PSYS_CURRENT; - } -} -Object *psys_find_object(Scene *scene, ParticleSystem *psys) -{ - Base *base = scene->base.first; - ParticleSystem *tpsys; - - for(base = scene->base.first; base; base = base->next) { - for(tpsys = base->object->particlesystem.first; psys; psys=psys->next) { - if(tpsys == psys) - return base->object; - } - } - - return NULL; -} /* change object's active particle system */ void psys_change_act(void *ob_v, void *act_v) { @@ -321,7 +293,7 @@ int psys_check_enabled(Object *ob, ParticleSystem *psys) ParticleSystemModifierData *psmd; Mesh *me; - if(psys->flag & PSYS_DISABLED || psys->flag & PSYS_DELETE || !psys->part) + if(psys->flag & PSYS_DISABLED || psys->flag & PSYS_DELETE) return 0; if(ob->type == OB_MESH) { @@ -892,7 +864,7 @@ static void weighted_particle_vector(float *v1, float *v2, float *v3, float *v4, vec[1]= weights[0]*v1[1] + weights[1]*v2[1] + weights[2]*v3[1] + weights[3]*v4[1]; vec[2]= weights[0]*v1[2] + weights[1]*v2[2] + weights[2]*v3[2] + weights[3]*v4[2]; } -void psys_interpolate_particle(short type, ParticleKey keys[4], float dt, ParticleKey *result, int velocity) +static void interpolate_particle(short type, ParticleKey keys[4], float dt, ParticleKey *result, int velocity) { float t[4]; @@ -2597,7 +2569,7 @@ void psys_cache_paths(Scene *scene, Object *ob, ParticleSystem *psys, float cfra } /* now we should have in chronologiacl order k1<=k2<=t<=k3<=k4 with keytime between [0,1]->[k2,k3] (k1 & k4 used for cardinal & bspline interpolation)*/ - psys_interpolate_particle((psys->flag & PSYS_KEYED) ? -1 /* signal for cubic interpolation */ + interpolate_particle((psys->flag & PSYS_KEYED) ? -1 /* signal for cubic interpolation */ : ((psys->part->flag & PART_HAIR_BSPLINE) ? KEY_BSPLINE : KEY_CARDINAL) ,keys, keytime, &result, 0); @@ -2929,61 +2901,6 @@ void psys_mat_hair_to_global(Object *ob, DerivedMesh *dm, short from, ParticleDa /************************************************/ /* ParticleSettings handling */ /************************************************/ -void object_add_particle_system_slot(Scene *scene, Object *ob) -{ - ParticleSystem *psys; - ModifierData *md; - ParticleSystemModifierData *psmd; - - if(!ob || ob->type != OB_MESH) - return; - - psys = ob->particlesystem.first; - for(; psys; psys=psys->next) - psys->flag &= ~PSYS_CURRENT; - - psys = MEM_callocN(sizeof(ParticleSystem), "particle_system"); - psys->pointcache = BKE_ptcache_add(); - BLI_addtail(&ob->particlesystem, psys); - - psys->part = psys_new_settings("PSys", NULL); - - md= modifier_new(eModifierType_ParticleSystem); - sprintf(md->name, "ParticleSystem %i", BLI_countlist(&ob->particlesystem)); - psmd= (ParticleSystemModifierData*) md; - psmd->psys=psys; - BLI_addtail(&ob->modifiers, md); - - psys->totpart=0; - psys->flag = PSYS_ENABLED|PSYS_CURRENT; - psys->cfra=bsystem_time(scene,ob,scene->r.cfra+1,0.0); - - DAG_scene_sort(scene); - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); -} -void object_remove_particle_system_slot(Scene *scene, Object *ob) -{ - ParticleSystem *psys = psys_get_current(ob); - ParticleSystemModifierData *psmd; - - if(!psys) - return; - - /* clear modifier */ - psmd= psys_get_modifier(ob, psys); - BLI_remlink(&ob->modifiers, psmd); - modifier_free((ModifierData *)psmd); - - /* clear particle system */ - BLI_remlink(&ob->particlesystem, psys); - psys_free(ob,psys); - - if(ob->particlesystem.first) - ((ParticleSystem *) ob->particlesystem.first)->flag |= PSYS_CURRENT; - - DAG_scene_sort(scene); - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); -} static void default_particle_settings(ParticleSettings *part) { int i; @@ -3070,9 +2987,6 @@ ParticleSettings *psys_new_settings(char *name, Main *main) { ParticleSettings *part; - if(main==NULL) - main = G.main; - part= alloc_libblock(&main->particle, ID_PA, name); default_particle_settings(part); @@ -3148,6 +3062,7 @@ void make_local_particlesettings(ParticleSettings *part) } } } + void psys_flush_particle_settings(Scene *scene, ParticleSettings *part, int recalc) { Base *base = scene->base.first; @@ -3580,7 +3495,7 @@ void psys_get_particle_on_path(Scene *scene, Object *ob, ParticleSystem *psys, i QuatInterpol(state->rot,keys[1].rot,keys[2].rot,keytime); } - psys_interpolate_particle((psys->flag & PSYS_KEYED) ? -1 /* signal for cubic interpolation */ + interpolate_particle((psys->flag & PSYS_KEYED) ? -1 /* signal for cubic interpolation */ : ((psys->part->flag & PART_HAIR_BSPLINE) ? KEY_BSPLINE : KEY_CARDINAL) ,keys, keytime, state, 1); @@ -3787,8 +3702,6 @@ int psys_get_particle_state(struct Scene *scene, Object *ob, ParticleSystem *psy if((pa->alive==PARS_UNBORN && (part->flag & PART_UNBORN)==0) || (pa->alive==PARS_DEAD && (part->flag & PART_DIED)==0)) return 0; - - state->time = MIN2(state->time, pa->dietime); } if(psys->flag & PSYS_KEYED){ @@ -3863,7 +3776,7 @@ int psys_get_particle_state(struct Scene *scene, Object *ob, ParticleSystem *psy VecMulf(keys[1].vel, dfra / frs_sec); VecMulf(keys[2].vel, dfra / frs_sec); - psys_interpolate_particle(-1, keys, keytime, state, 1); + interpolate_particle(-1, keys, keytime, state, 1); /* convert back to real velocity */ VecMulf(state->vel, frs_sec / dfra); diff --git a/source/blender/blenkernel/intern/particle_system.c b/source/blender/blenkernel/intern/particle_system.c index 591b6ca9be5..52f13eeadb8 100644 --- a/source/blender/blenkernel/intern/particle_system.c +++ b/source/blender/blenkernel/intern/particle_system.c @@ -29,8 +29,6 @@ * ***** END GPL LICENSE BLOCK ***** */ -#include "BLI_storage.h" /* _LARGEFILE_SOURCE */ - #include <stdlib.h> #include <math.h> #include <string.h> @@ -106,8 +104,7 @@ static int get_current_display_percentage(ParticleSystem *psys) { ParticleSettings *part=psys->part; - if(psys->renderdata || (part->child_nbr && part->childtype) - || (psys->pointcache->flag & PTCACHE_BAKING)) + if(psys->renderdata || (part->child_nbr && part->childtype)) return 100; if(part->phystype==PART_PHYS_KEYED){ @@ -2198,91 +2195,57 @@ void psys_get_reactor_target(Object *ob, ParticleSystem *psys, Object **target_o /************************************************/ /* Point Cache */ /************************************************/ -void psys_get_pointcache_start_end(Scene *scene, ParticleSystem *psys, int *sfra, int *efra) -{ - ParticleSettings *part = psys->part; - - *sfra = MAX2(1, (int)part->sta); - *efra = MIN2((int)(part->end + part->lifetime + 1.0), scene->r.efra); -} -static void particle_write_state(int index, ParticleSystem *psys, float *data) -{ - memcpy(data, (float *)(&(psys->particles+index)->state), sizeof(ParticleKey)); -} -static void particle_read_state(int index, void *psys_ptr, float *data) -{ - ParticleSystem *psys= psys_ptr; - ParticleData *pa = psys->particles + index; - ParticleKey *key = (ParticleKey *)data; - - if(key->time > pa->state.time) - copy_particle_key(&pa->prev_state, &pa->state, 1); - - copy_particle_key(&pa->state, key, 1); -} -static void particle_cache_interpolate(int index, void *psys_ptr, float frs_sec, float cfra, float cfra1, float cfra2, float *data1, float *data2) -{ - ParticleSystem *psys= psys_ptr; - ParticleData *pa = psys->particles + index; - ParticleKey keys[4]; - float dfra, cfra1f = (float)cfra1, cfra2f(float); - - cfra = MIN2(cfra, pa->dietime); - cfra1 = MIN2(cfra1, pa->dietime); - cfra2 = MIN2(cfra2, pa->dietime); - - keys[1] = *((ParticleKey*)data1); - keys[2] = *((ParticleKey*)data2); - - if(cfra1 == cfra2) { - copy_particle_key(&pa->state, &keys[1], 1); - return; - } - - dfra = cfra2 - cfra1; - - VecMulf(keys[1].vel, dfra / frs_sec); - VecMulf(keys[2].vel, dfra / frs_sec); - psys_interpolate_particle(-1, keys, (cfra - cfra1) / dfra, &pa->state, 1); - - VecMulf(pa->state.vel, frs_sec / dfra); - - pa->state.time = cfra; -} static void write_particles_to_cache(Object *ob, ParticleSystem *psys, int cfra) { - PTCacheWriter writer; PTCacheID pid; + PTCacheFile *pf; + ParticleData *pa; + int i, totpart= psys->totpart; - BKE_ptcache_id_from_particles(&pid, ob, psys); + if(totpart == 0) + return; - writer.calldata = psys; - writer.cfra = cfra; - writer.set_elem = particle_write_state; - writer.pid = &pid; - writer.totelem = psys->totpart; + BKE_ptcache_id_from_particles(&pid, ob, psys); + pf= BKE_ptcache_file_open(&pid, PTCACHE_FILE_WRITE, cfra); + if(!pf) + return; - BKE_ptcache_write_cache(&writer); + /* assuming struct consists of tightly packed floats */ + for(i=0, pa=psys->particles; i<totpart; i++, pa++) + BKE_ptcache_file_write_floats(pf, (float*)&pa->state, sizeof(ParticleKey)/sizeof(float)); + + BKE_ptcache_file_close(pf); } -static int get_particles_from_cache(Scene *scene, Object *ob, ParticleSystem *psys, float cfra, int *old_frame) +static int get_particles_from_cache(Object *ob, ParticleSystem *psys, int cfra) { - PTCacheReader reader; PTCacheID pid; - + PTCacheFile *pf; + ParticleData *pa; + int i, totpart= psys->totpart; + + if(totpart == 0) + return 0; + BKE_ptcache_id_from_particles(&pid, ob, psys); + pf= BKE_ptcache_file_open(&pid, PTCACHE_FILE_READ, cfra); + if(!pf) + return 0; - reader.calldata = psys; - reader.cfra = cfra; - reader.interpolate_elem = particle_cache_interpolate; - reader.old_frame = old_frame; - reader.pid = &pid; - reader.scene = scene; - reader.set_elem = particle_read_state; - reader.totelem = psys->totpart; + /* assuming struct consists of tightly packed floats */ + for(i=0, pa=psys->particles; i<totpart; i++, pa++) { + if(cfra!=pa->state.time) + copy_particle_key(&pa->prev_state,&pa->state,1); + if(!BKE_ptcache_file_read_floats(pf, (float*)&pa->state, sizeof(ParticleKey)/sizeof(float))) { + BKE_ptcache_file_close(pf); + return 0; + } + } + + BKE_ptcache_file_close(pf); - return BKE_ptcache_read_cache(&reader); + return 1; } /************************************************/ @@ -2409,8 +2372,6 @@ static void add_to_effectors(ListBase *lb, Scene *scene, Object *ob, Object *obs Object *tob; for(i=0; epsys; epsys=epsys->next,i++){ - if(!psys_check_enabled(ob, epsys)) - continue; type=0; if(epsys!=psys || (psys->part->flag & PART_SELF_EFFECT)){ epart=epsys->part; @@ -4124,7 +4085,7 @@ static void dynamics_step(Scene *scene, Object *ob, ParticleSystem *psys, Partic /* main loop: calculate physics for all particles */ for(p=0, pa=psys->particles; p<totpart; p++,pa++){ - if(pa->flag & (PARS_UNEXIST+PARS_NO_DISP)) continue; + if(pa->flag & PARS_UNEXIST) continue; copy_particle_key(&pa->prev_state,&pa->state,1); @@ -4149,26 +4110,25 @@ static void dynamics_step(Scene *scene, Object *ob, ParticleSystem *psys, Partic if(pa->alive==PARS_UNBORN || pa->alive==PARS_KILLED || ELEM(part->phystype,PART_PHYS_NO,PART_PHYS_KEYED) - || birthtime >= psys->cfra){ + || birthtime >= cfra){ reset_particle(scene, pa,psys,psmd,ob,dtime,cfra,vg_vel,vg_tan,vg_rot); } pa_dfra = dfra; pa_dtime = dtime; - - if(dietime <= cfra && psys->cfra < dietime){ - /* particle dies some time between this and last step */ - pa_dfra = dietime - ((birthtime > psys->cfra) ? birthtime : psys->cfra); - pa_dtime = pa_dfra * timestep; - pa->alive = PARS_DYING; - } - else if(birthtime <= cfra && birthtime >= psys->cfra){ + if(birthtime <= cfra && birthtime >= psys->cfra){ /* particle is born some time between this and last step*/ pa->alive = PARS_ALIVE; pa_dfra = cfra - birthtime; pa_dtime = pa_dfra*timestep; } + else if(dietime <= cfra && psys->cfra < dietime){ + /* particle dies some time between this and last step */ + pa_dfra = dietime - psys->cfra; + pa_dtime = pa_dfra * timestep; + pa->alive = PARS_DYING; + } else if(dietime < cfra){ /* nothing to be done when particle is dead */ } @@ -4375,7 +4335,7 @@ static void cached_step(Scene *scene, Object *ob, ParticleSystemModifierData *ps pa->alive = PARS_UNBORN; else if(dietime <= cfra){ if(dietime > psys->cfra){ - state.time = dietime; + state.time = pa->dietime; psys_get_particle_state(scene, ob,psys,p,&state,1); push_reaction(ob,psys,p,PART_EVENT_DEATH,&state); } @@ -4560,7 +4520,7 @@ static void system_step(Scene *scene, Object *ob, ParticleSystem *psys, Particle int totpart, oldtotpart, totchild, oldtotchild, p; float disp, *vg_vel= 0, *vg_tan= 0, *vg_rot= 0, *vg_size= 0; int init= 0, distr= 0, alloc= 0, usecache= 0, only_children_changed= 0; - int framenr, framedelta, startframe, endframe, old_framenr; + int framenr, framedelta, startframe, endframe; part= psys->part; cache= psys->pointcache; @@ -4568,10 +4528,6 @@ static void system_step(Scene *scene, Object *ob, ParticleSystem *psys, Particle framenr= (int)scene->r.cfra; framedelta= framenr - cache->simframe; - /* set suitable cache range automatically */ - if((cache->flag & (PTCACHE_BAKING|PTCACHE_BAKED))==0) - psys_get_pointcache_start_end(scene, psys, &cache->startframe, &cache->endframe); - BKE_ptcache_id_from_particles(&pid, ob, psys); BKE_ptcache_id_time(&pid, scene, 0.0f, &startframe, &endframe, NULL); @@ -4644,13 +4600,9 @@ static void system_step(Scene *scene, Object *ob, ParticleSystem *psys, Particle if(init) { if(distr) { - if(alloc) { + if(alloc) realloc_particles(ob, psys, totpart); - if(usecache) - BKE_ptcache_id_clear(&pid, PTCACHE_CLEAR_ALL, 0); - } - distribute_particles(scene, ob, psys, part->from); if((psys->part->type == PART_HAIR) && !(psys->flag & PSYS_HAIR_DONE)) @@ -4664,11 +4616,9 @@ static void system_step(Scene *scene, Object *ob, ParticleSystem *psys, Particle free_keyed_keys(psys); initialize_all_particles(ob, psys, psmd); - - if(alloc) { + if(alloc) reset_all_particles(scene, ob, psys, psmd, 0.0, cfra, oldtotpart); - } } /* flag for possible explode modifiers after this system */ @@ -4677,59 +4627,46 @@ static void system_step(Scene *scene, Object *ob, ParticleSystem *psys, Particle /* try to read from the cache */ if(usecache) { - int result = get_particles_from_cache(scene, ob, psys, (float)framenr, &old_framenr); - - if(result == PTCACHE_READ_EXACT || result == PTCACHE_READ_INTERPOLATED) { - //if(part->phystype==PART_PHYS_KEYED && psys->flag&PSYS_FIRST_KEYED) { - // psys_count_keyed_targets(ob,psys); - // set_keyed_keys(scene, ob, psys); - //} + if(get_particles_from_cache(ob, psys, framenr)) { + if(part->phystype==PART_PHYS_KEYED && psys->flag&PSYS_FIRST_KEYED) { + psys_count_keyed_targets(ob,psys); + set_keyed_keys(scene, ob, psys); + } cached_step(scene, ob, psmd, psys, cfra); psys->cfra=cfra; psys->recalc = 0; - //if(part->phystype==PART_PHYS_KEYED && psys->flag&PSYS_FIRST_KEYED) { - // psys_update_path_cache(scene, ob, psmd, psys, framenr); - //} + if(part->phystype==PART_PHYS_KEYED && psys->flag&PSYS_FIRST_KEYED) { + psys_update_path_cache(scene, ob, psmd, psys, framenr); + } cache->simframe= framenr; cache->flag |= PTCACHE_SIMULATION_VALID; - if(result == PTCACHE_READ_INTERPOLATED && cache->flag & PTCACHE_REDO_NEEDED) - write_particles_to_cache(ob, psys, cfra); - return; } - else if(result==PTCACHE_READ_OLD) { - /* set old cfra */ - psys->cfra = (float)old_framenr; - - for(p=0, pa=psys->particles; p<totpart; p++, pa++) { - /* update alive status */ - if(pa->time > psys->cfra) - pa->alive = PARS_UNBORN; - else if(pa->dietime <= psys->cfra) - pa->alive = PARS_DEAD; - else - pa->alive = PARS_ALIVE; - } - } else if(ob->id.lib || (cache->flag & PTCACHE_BAKED)) { psys_reset(psys, PSYS_RESET_CACHE_MISS); psys->cfra=cfra; psys->recalc = 0; return; } + + if(framenr != startframe && framedelta != 1) { + psys_reset(psys, PSYS_RESET_CACHE_MISS); + psys->cfra = cfra; + psys->recalc = 0; + return; + } } else { cache->flag &= ~PTCACHE_SIMULATION_VALID; cache->simframe= 0; - cache->last_exact= 0; } /* if on second frame, write cache for first frame */ - if(usecache && psys->cfra == startframe && (cache->flag & PTCACHE_OUTDATED || cache->last_exact==0)) + if(usecache && framenr == startframe+1) write_particles_to_cache(ob, psys, startframe); if(part->phystype==PART_PHYS_KEYED && psys->flag&PSYS_FIRST_KEYED) @@ -4831,7 +4768,8 @@ static void psys_to_softbody(Scene *scene, Object *ob, ParticleSystem *psys) static int hair_needs_recalc(ParticleSystem *psys) { if((psys->flag & PSYS_EDITED)==0 && - ((psys->flag & PSYS_HAIR_DONE)==0 || psys->recalc & PSYS_RECALC_RESET)) { + ((psys->flag & PSYS_HAIR_DONE)==0 || psys->recalc & PSYS_RECALC_REDO)) { + psys->recalc &= ~PSYS_RECALC_REDO; return 1; } diff --git a/source/blender/blenkernel/intern/pointcache.c b/source/blender/blenkernel/intern/pointcache.c index 64473d07151..b00755f7135 100644 --- a/source/blender/blenkernel/intern/pointcache.c +++ b/source/blender/blenkernel/intern/pointcache.c @@ -51,11 +51,9 @@ #include "BKE_object.h" #include "BKE_particle.h" #include "BKE_pointcache.h" -#include "BKE_scene.h" #include "BKE_softbody.h" #include "BKE_utildefines.h" -#include "BLI_blenlib.h" /* needed for directory lookup */ #ifndef WIN32 @@ -215,29 +213,21 @@ static int BKE_ptcache_id_filename(PTCacheID *pid, char *filename, int cfra, sho filename[0] = '\0'; newname = filename; - if (!G.relbase_valid) return 0; /* save blend file before using disk pointcache */ + /*if (!G.relbase_valid) return 0; *//* save blend file before using pointcache */ /* start with temp dir */ if (do_path) { len = ptcache_path(pid, filename); newname += len; } - if(strcmp(pid->cache->name, "")==0) { - idname = (pid->ob->id.name+2); - /* convert chars to hex so they are always a valid filename */ - while('\0' != *idname) { - snprintf(newname, MAX_PTCACHE_FILE, "%02X", (char)(*idname++)); - newname+=2; - len += 2; - } + idname = (pid->ob->id.name+2); + /* convert chars to hex so they are always a valid filename */ + while('\0' != *idname) { + snprintf(newname, MAX_PTCACHE_FILE, "%02X", (char)(*idname++)); + newname+=2; + len += 2; } - else { - int temp = strlen(pid->cache->name); - strcpy(newname, pid->cache->name); - newname+=temp; - len += temp; - } - + if (do_ext) { snprintf(newname, MAX_PTCACHE_FILE, "_%06d_%02d"PTCACHE_EXT, cfra, pid->stack_index); /* always 6 chars */ len += 16; @@ -257,7 +247,7 @@ PTCacheFile *BKE_ptcache_file_open(PTCacheID *pid, int mode, int cfra) if(pid->ob->id.lib && mode == PTCACHE_FILE_WRITE) return NULL; - if (!G.relbase_valid) return NULL; /* save blend file before using disk pointcache */ + /*if (!G.relbase_valid) return NULL; *//* save blend file before using pointcache */ BKE_ptcache_id_filename(pid, filename, cfra, 1, 1); @@ -296,427 +286,6 @@ int BKE_ptcache_file_write_floats(PTCacheFile *pf, float *f, int tot) return (fwrite(f, sizeof(float), tot, pf->fp) == tot); } -static int ptcache_pid_elemsize(PTCacheID *pid) -{ - if(pid->type==PTCACHE_TYPE_SOFTBODY) - return 0; // TODO - else if(pid->type==PTCACHE_TYPE_PARTICLES) - return sizeof(ParticleKey); - else if(pid->type==PTCACHE_TYPE_CLOTH) - return 9 * sizeof(float); - - return 0; -} -static int ptcache_pid_totelem(PTCacheID *pid) -{ - if(pid->type==PTCACHE_TYPE_SOFTBODY) - return 0; // TODO - else if(pid->type==PTCACHE_TYPE_PARTICLES) { - ParticleSystem *psys = pid->data; - return psys->totpart; - } - else if(pid->type==PTCACHE_TYPE_CLOTH) - return 0; // TODO - - return 0; -} - -void BKE_ptcache_update_info(PTCacheID *pid) -{ - PointCache *cache = pid->cache; - int totframes = 0; - char mem_info[64]; - - if(cache->flag & PTCACHE_DISK_CACHE) { - int cfra = cache->startframe; - - for(; cfra<=cache->endframe; cfra++) { - if(BKE_ptcache_id_exist(pid, cfra)) - totframes++; - } - - sprintf(mem_info, "%i frames on disk", totframes); - } - else { - PTCacheMem *pm = cache->mem_cache.first; - float framesize = 0.0f, bytes = 0.0f; - int mb; - - if(pm) - framesize = (float)ptcache_pid_elemsize(pid) * (float)pm->totpoint; - - for(; pm; pm=pm->next) - totframes++; - - bytes = totframes * framesize; - - mb = (bytes > 1024.0f * 1024.0f); - - sprintf(mem_info, "%i frames in memory (%.1f %s)", - totframes, - bytes / (mb ? 1024.0f * 1024.0f : 1024.0f), - mb ? "Mb" : "kb"); - } - - if(cache->flag & PTCACHE_OUTDATED) { - sprintf(cache->info, "%s, cache is outdated!", mem_info); - } - else if(cache->flag & PTCACHE_FRAMES_SKIPPED) { - sprintf(cache->info, "%s, not exact since frame %i.", mem_info, cache->last_exact); - } - else - sprintf(cache->info, "%s.", mem_info); -} -/* reads cache from disk or memory */ -/* possible to get old or interpolated result */ -int BKE_ptcache_read_cache(PTCacheReader *reader) -{ - PTCacheID *pid = reader->pid; - PTCacheFile *pf=NULL, *pf2=NULL; - PTCacheMem *pm=NULL, *pm2=NULL; - int totelem = reader->totelem; - float cfra = reader->cfra; - int cfrai = (int)cfra; - int elemsize = ptcache_pid_elemsize(pid); - int i, incr = elemsize / sizeof(float); - float frs_sec = reader->scene->r.frs_sec; - int cfra1=0, cfra2; - int ret = 0; - - if(totelem == 0) - return 0; - - - /* first check if we have the actual frame cached */ - if(cfra == (float)cfrai) { - if(pid->cache->flag & PTCACHE_DISK_CACHE) { - pf= BKE_ptcache_file_open(pid, PTCACHE_FILE_READ, cfrai); - } - else { - pm = pid->cache->mem_cache.first; - - for(; pm; pm=pm->next) { - if(pm->frame == cfrai) - break; - } - } - } - - /* if found, use exact frame */ - if(pf || pm) { - float *data; - - if(pm) - data = pm->data; - else - data = MEM_callocN(elemsize, "pointcache read data"); - - for(i=0; i<totelem; i++) { - if(pf) { - if(!BKE_ptcache_file_read_floats(pf, data, incr)) { - BKE_ptcache_file_close(pf); - MEM_freeN(data); - return 0; - } - - reader->set_elem(i, reader->calldata, data); - } - else { - reader->set_elem(i, reader->calldata, data); - data += incr; - } - } - - if(pf) { - BKE_ptcache_file_close(pf); - MEM_freeN(data); - } - - ret = PTCACHE_READ_EXACT; - } - - if(ret) - ; - /* no exact cache frame found so try to find cached frames around cfra */ - else if(pid->cache->flag & PTCACHE_DISK_CACHE) { - pf=NULL; - while(cfrai > pid->cache->startframe && !pf) { - cfrai--; - pf= BKE_ptcache_file_open(pid, PTCACHE_FILE_READ, cfrai); - cfra1 = cfrai; - } - - if(reader->old_frame) - *(reader->old_frame) = cfrai; - - cfrai = (int)cfra; - while(cfrai < pid->cache->endframe && !pf2) { - cfrai++; - pf2= BKE_ptcache_file_open(pid, PTCACHE_FILE_READ, cfrai); - cfra2 = cfrai; - } - } - else if(pid->cache->mem_cache.first){ - pm = pid->cache->mem_cache.first; - - while(pm->next && pm->next->frame < cfra) - pm= pm->next; - - if(pm) { - if(reader->old_frame) - *(reader->old_frame) = pm->frame; - cfra1 = pm->frame; - } - - pm2 = pid->cache->mem_cache.last; - - if(pm2 && pm2->frame < cfra) - pm2 = NULL; - else { - while(pm2->prev && pm2->prev->frame > cfra) - pm2= pm2->prev; - - if(pm2) - cfra2 = pm2->frame; - } - } - - if(ret) - ; - else if((pf && pf2) || (pm && pm2)) { - /* interpolate from nearest frames if cache isn't outdated */ - float *data1, *data2; - - if(pm) { - data1 = pm->data; - data2 = pm2->data; - } - else { - data1 = MEM_callocN(elemsize, "pointcache read data1"); - data2 = MEM_callocN(elemsize, "pointcache read data2"); - } - - for(i=0; i<totelem; i++) { - if(pf && pf2) { - if(!BKE_ptcache_file_read_floats(pf, data1, incr)) { - BKE_ptcache_file_close(pf); - BKE_ptcache_file_close(pf2); - MEM_freeN(data1); - MEM_freeN(data2); - return 0; - } - if(!BKE_ptcache_file_read_floats(pf2, data2, incr)) { - BKE_ptcache_file_close(pf); - BKE_ptcache_file_close(pf2); - MEM_freeN(data1); - MEM_freeN(data2); - return 0; - } - reader->interpolate_elem(i, reader->calldata, frs_sec, cfra, (float)cfra1, (float)cfra2, data1, data2); - } - else { - reader->interpolate_elem(i, reader->calldata, frs_sec, cfra, (float)cfra1, (float)cfra2, data1, data2); - data1 += incr; - data2 += incr; - } - } - - if(pf) { - BKE_ptcache_file_close(pf); - BKE_ptcache_file_close(pf2); - MEM_freeN(data1); - MEM_freeN(data2); - } - - ret = PTCACHE_READ_INTERPOLATED; - } - else if(pf || pm) { - /* use last valid cache frame */ - float *data; - - /* don't read cache if allready simulated past cached frame */ - if(cfra1 && cfra1 <= pid->cache->simframe) { - if(pf) - BKE_ptcache_file_close(pf); - if(pf2) - BKE_ptcache_file_close(pf2); - - return 0; - } - - if(pm) - data = pm->data; - else - data = MEM_callocN(elemsize, "pointcache read data"); - - for(i=0; i<totelem; i++) { - if(pf) { - if(!BKE_ptcache_file_read_floats(pf, data, incr)) { - BKE_ptcache_file_close(pf); - if(pf2) - BKE_ptcache_file_close(pf2); - return 0; - } - reader->set_elem(i, reader->calldata, data); - } - else { - reader->set_elem(i, reader->calldata, data); - data += incr; - } - } - - if(pf) { - BKE_ptcache_file_close(pf); - MEM_freeN(data); - } - if(pf2) - BKE_ptcache_file_close(pf2); - - ret = PTCACHE_READ_OLD; - } - - if(pf) - BKE_ptcache_file_close(pf); - if(pf2) - BKE_ptcache_file_close(pf2); - - if((pid->cache->flag & PTCACHE_QUICK_CACHE)==0) { - /* clear invalid cache frames so that better stuff can be simulated */ - if(pid->cache->flag & PTCACHE_OUTDATED) { - BKE_ptcache_id_clear(pid, PTCACHE_CLEAR_AFTER, cfra); - } - else if(pid->cache->flag & PTCACHE_FRAMES_SKIPPED) { - if(cfra <= pid->cache->last_exact) - pid->cache->flag &= ~PTCACHE_FRAMES_SKIPPED; - - BKE_ptcache_id_clear(pid, PTCACHE_CLEAR_AFTER, MAX2(cfra,pid->cache->last_exact)); - } - } - - return ret; -} -/* writes cache to disk or memory */ -int BKE_ptcache_write_cache(PTCacheWriter *writer) -{ - PointCache *cache = writer->pid->cache; - PTCacheFile *pf= NULL; - int elemsize = ptcache_pid_elemsize(writer->pid); - int i, incr = elemsize / sizeof(float); - int add = 0, overwrite = 0, ocfra; - float temp[14]; - - if(writer->totelem == 0 || writer->cfra <= 0) - return 0; - - if(cache->flag & PTCACHE_DISK_CACHE) { - /* allways start from scratch on the first frame */ - if(writer->cfra == cache->startframe) { - BKE_ptcache_id_clear(writer->pid, PTCACHE_CLEAR_ALL, writer->cfra); - cache->flag &= ~PTCACHE_REDO_NEEDED; - add = 1; - } - else { - int cfra = cache->endframe; - /* find last cached frame */ - while(cfra > cache->startframe && !BKE_ptcache_id_exist(writer->pid, cfra)) - cfra--; - - /* find second last cached frame */ - ocfra = cfra-1; - while(ocfra > cache->startframe && !BKE_ptcache_id_exist(writer->pid, ocfra)) - ocfra--; - - if(writer->cfra > cfra) { - if(ocfra >= cache->startframe && cfra - ocfra < cache->step) - overwrite = 1; - else - add = 1; - } - } - - if(add || overwrite) { - if(overwrite) - BKE_ptcache_id_clear(writer->pid, PTCACHE_CLEAR_FRAME, ocfra); - - pf = BKE_ptcache_file_open(writer->pid, PTCACHE_FILE_WRITE, writer->cfra); - if(!pf) - return 0; - - for(i=0; i<writer->totelem; i++) { - writer->set_elem(i, writer->calldata, &temp); - BKE_ptcache_file_write_floats(pf, &temp, incr); - } - } - } - else { - PTCacheMem *pm; - PTCacheMem *pm2; - float *pmdata; - - pm2 = cache->mem_cache.first; - - /* allways start from scratch on the first frame */ - if(writer->cfra == cache->startframe) { - BKE_ptcache_id_clear(writer->pid, PTCACHE_CLEAR_ALL, writer->cfra); - cache->flag &= ~PTCACHE_REDO_NEEDED; - add = 1; - } - else { - pm2 = cache->mem_cache.last; - - if(pm2 && writer->cfra > pm2->frame) { - if(pm2 && pm2->prev && pm2->frame - pm2->prev->frame < cache->step) - overwrite = 1; - else - add = 1; - } - } - - if(overwrite) { - pm = cache->mem_cache.last; - pmdata = pm->data; - - for(i=0; i<writer->totelem; i++, pmdata+=incr) { - writer->set_elem(i, writer->calldata, &temp); - memcpy(pmdata, &temp, elemsize); - } - - pm->frame = writer->cfra; - } - else if(add) { - pm = MEM_callocN(sizeof(PTCacheMem), "Pointcache mem"); - pm->data = MEM_callocN(elemsize * writer->totelem, "Pointcache mem data"); - pmdata = pm->data; - - for(i=0; i<writer->totelem; i++, pmdata+=incr) { - writer->set_elem(i, writer->calldata, &temp); - memcpy(pmdata, &temp, elemsize); - } - - pm->frame = writer->cfra; - pm->totpoint = writer->totelem; - - BLI_addtail(&cache->mem_cache, pm); - } - } - - if(add || overwrite) { - if(writer->cfra - cache->last_exact == 1 - || writer->cfra == cache->startframe) { - cache->last_exact = writer->cfra; - cache->flag &= ~PTCACHE_FRAMES_SKIPPED; - } - else - cache->flag |= PTCACHE_FRAMES_SKIPPED; - } - - if(pf) - BKE_ptcache_file_close(pf); - - BKE_ptcache_update_info(writer->pid); - - return 1; -} /* youll need to close yourself after! * mode - PTCACHE_CLEAR_ALL, @@ -748,116 +317,62 @@ void BKE_ptcache_id_clear(PTCacheID *pid, int mode, int cfra) case PTCACHE_CLEAR_ALL: case PTCACHE_CLEAR_BEFORE: case PTCACHE_CLEAR_AFTER: - if(pid->cache->flag & PTCACHE_DISK_CACHE) { - ptcache_path(pid, path); - - len = BKE_ptcache_id_filename(pid, filename, cfra, 0, 0); /* no path */ - - dir = opendir(path); - if (dir==NULL) - return; - - snprintf(ext, sizeof(ext), "_%02d"PTCACHE_EXT, pid->stack_index); - - while ((de = readdir(dir)) != NULL) { - if (strstr(de->d_name, ext)) { /* do we have the right extension?*/ - if (strncmp(filename, de->d_name, len ) == 0) { /* do we have the right prefix */ - if (mode == PTCACHE_CLEAR_ALL) { - pid->cache->last_exact = 0; - BLI_join_dirfile(path_full, path, de->d_name); - BLI_delete(path_full, 0, 0); - } else { - /* read the number of the file */ - int frame, len2 = strlen(de->d_name); - char num[7]; - - if (len2 > 15) { /* could crash if trying to copy a string out of this range*/ - BLI_strncpy(num, de->d_name + (strlen(de->d_name) - 15), sizeof(num)); - frame = atoi(num); + ptcache_path(pid, path); + + len = BKE_ptcache_id_filename(pid, filename, cfra, 0, 0); /* no path */ + + dir = opendir(path); + if (dir==NULL) + return; + + snprintf(ext, sizeof(ext), "_%02d"PTCACHE_EXT, pid->stack_index); + + while ((de = readdir(dir)) != NULL) { + if (strstr(de->d_name, ext)) { /* do we have the right extension?*/ + if (strncmp(filename, de->d_name, len ) == 0) { /* do we have the right prefix */ + if (mode == PTCACHE_CLEAR_ALL) { + BLI_join_dirfile(path_full, path, de->d_name); + BLI_delete(path_full, 0, 0); + } else { + /* read the number of the file */ + int frame, len2 = strlen(de->d_name); + char num[7]; + + if (len2 > 15) { /* could crash if trying to copy a string out of this range*/ + BLI_strncpy(num, de->d_name + (strlen(de->d_name) - 15), sizeof(num)); + frame = atoi(num); + + if((mode==PTCACHE_CLEAR_BEFORE && frame < cfra) || + (mode==PTCACHE_CLEAR_AFTER && frame > cfra) ) { - if((mode==PTCACHE_CLEAR_BEFORE && frame < cfra) || - (mode==PTCACHE_CLEAR_AFTER && frame > cfra) ) { - - BLI_join_dirfile(path_full, path, de->d_name); - BLI_delete(path_full, 0, 0); - } + BLI_join_dirfile(path_full, path, de->d_name); + BLI_delete(path_full, 0, 0); } } } } } - closedir(dir); - } - else { - PTCacheMem *pm= pid->cache->mem_cache.first; - PTCacheMem *link= NULL; - - if(mode == PTCACHE_CLEAR_ALL) { - pid->cache->last_exact = 0; - for(; pm; pm=pm->next) - MEM_freeN(pm->data); - BLI_freelistN(&pid->cache->mem_cache); - } else { - while(pm) { - if((mode==PTCACHE_CLEAR_BEFORE && pm->frame < cfra) || - (mode==PTCACHE_CLEAR_AFTER && pm->frame > cfra) ) { - link = pm; - pm = pm->next; - MEM_freeN(link->data); - BLI_freelinkN(&pid->cache->mem_cache, link); - } - else - pm = pm->next; - } - } } + closedir(dir); break; case PTCACHE_CLEAR_FRAME: - if(pid->cache->flag & PTCACHE_DISK_CACHE) { - if(BKE_ptcache_id_exist(pid, cfra)) { - BKE_ptcache_id_filename(pid, filename, cfra, 1, 1); /* no path */ - BLI_delete(filename, 0, 0); - } - } - else { - PTCacheMem *pm = pid->cache->mem_cache.first; - - for(; pm; pm=pm->next) { - if(pm->frame == cfra) { - MEM_freeN(pm->data); - BLI_freelinkN(&pid->cache->mem_cache, pm); - break; - } - } - } + len = BKE_ptcache_id_filename(pid, filename, cfra, 1, 1); /* no path */ + BLI_delete(filename, 0, 0); break; } - - BKE_ptcache_update_info(pid); } int BKE_ptcache_id_exist(PTCacheID *pid, int cfra) { + char filename[MAX_PTCACHE_FILE]; + if(!pid->cache) return 0; - if(pid->cache->flag & PTCACHE_DISK_CACHE) { - char filename[MAX_PTCACHE_FILE]; - - BKE_ptcache_id_filename(pid, filename, cfra, 1, 1); - - return BLI_exists(filename); - } - else { - PTCacheMem *pm = pid->cache->mem_cache.first; + BKE_ptcache_id_filename(pid, filename, cfra, 1, 1); - for(; pm; pm=pm->next) { - if(pm->frame==cfra) - return 1; - } - return 0; - } + return BLI_exists(filename); } void BKE_ptcache_id_time(PTCacheID *pid, Scene *scene, float cfra, int *startframe, int *endframe, float *timescale) @@ -866,9 +381,6 @@ void BKE_ptcache_id_time(PTCacheID *pid, Scene *scene, float cfra, int *startfra PointCache *cache; float offset, time, nexttime; - /* TODO: this has to be sorter out once bsystem_time gets redone, */ - /* now caches can handle interpolating etc. too - jahka */ - /* time handling for point cache: * - simulation time is scaled by result of bsystem_time * - for offsetting time only time offset is taken into account, since @@ -902,10 +414,10 @@ void BKE_ptcache_id_time(PTCacheID *pid, Scene *scene, float cfra, int *startfra } } -int BKE_ptcache_id_reset(Scene *scene, PTCacheID *pid, int mode) +int BKE_ptcache_id_reset(PTCacheID *pid, int mode) { PointCache *cache; - int reset, clear, after; + int reset, clear; if(!pid->cache) return 0; @@ -913,17 +425,14 @@ int BKE_ptcache_id_reset(Scene *scene, PTCacheID *pid, int mode) cache= pid->cache; reset= 0; clear= 0; - after= 0; if(mode == PTCACHE_RESET_DEPSGRAPH) { if(!(cache->flag & PTCACHE_BAKED) && !BKE_ptcache_get_continue_physics()) { - if(cache->flag & PTCACHE_QUICK_CACHE) - clear= 1; - - after= 1; + reset= 1; + clear= 1; } - - cache->flag |= PTCACHE_OUTDATED; + else + cache->flag |= PTCACHE_OUTDATED; } else if(mode == PTCACHE_RESET_BAKED) { if(!BKE_ptcache_get_continue_physics()) { @@ -942,9 +451,8 @@ int BKE_ptcache_id_reset(Scene *scene, PTCacheID *pid, int mode) } if(reset) { - cache->flag &= ~(PTCACHE_REDO_NEEDED|PTCACHE_SIMULATION_VALID); + cache->flag &= ~(PTCACHE_OUTDATED|PTCACHE_SIMULATION_VALID); cache->simframe= 0; - cache->last_exact= 0; if(pid->type == PTCACHE_TYPE_CLOTH) cloth_free_modifier(pid->ob, pid->data); @@ -955,13 +463,11 @@ int BKE_ptcache_id_reset(Scene *scene, PTCacheID *pid, int mode) } if(clear) BKE_ptcache_id_clear(pid, PTCACHE_CLEAR_ALL, 0); - else if(after) - BKE_ptcache_id_clear(pid, PTCACHE_CLEAR_AFTER, CFRA); - return (reset || clear || after); + return (reset || clear); } -int BKE_ptcache_object_reset(Scene *scene, Object *ob, int mode) +int BKE_ptcache_object_reset(Object *ob, int mode) { PTCacheID pid; ParticleSystem *psys; @@ -973,7 +479,7 @@ int BKE_ptcache_object_reset(Scene *scene, Object *ob, int mode) if(ob->soft) { BKE_ptcache_id_from_softbody(&pid, ob, ob->soft); - reset |= BKE_ptcache_id_reset(scene, &pid, mode); + reset |= BKE_ptcache_id_reset(&pid, mode); } for(psys=ob->particlesystem.first; psys; psys=psys->next) { @@ -982,23 +488,23 @@ int BKE_ptcache_object_reset(Scene *scene, Object *ob, int mode) if(psys->soft) { BKE_ptcache_id_from_softbody(&pid, ob, psys->soft); if(mode == PSYS_RESET_ALL || !(psys->part->type == PART_HAIR && (pid.cache->flag & PTCACHE_BAKED))) - reset |= BKE_ptcache_id_reset(scene, &pid, mode); + reset |= BKE_ptcache_id_reset(&pid, mode); else skip = 1; } - else if(psys->recalc & PSYS_RECALC_REDO || psys->recalc & PSYS_RECALC_CHILD) + else if((psys->recalc & PSYS_RECALC_RESET)==0) skip = 1; if(skip == 0) { BKE_ptcache_id_from_particles(&pid, ob, psys); - reset |= BKE_ptcache_id_reset(scene, &pid, mode); + reset |= BKE_ptcache_id_reset(&pid, mode); } } for(md=ob->modifiers.first; md; md=md->next) { if(md->type == eModifierType_Cloth) { BKE_ptcache_id_from_cloth(&pid, ob, (ClothModifierData*)md); - reset |= BKE_ptcache_id_reset(scene, &pid, mode); + reset |= BKE_ptcache_id_reset(&pid, mode); } } @@ -1058,7 +564,7 @@ void BKE_ptcache_set_continue_physics(Scene *scene, int enable) if(CONTINUE_PHYSICS == 0) { for(ob=G.main->object.first; ob; ob=ob->id.next) - if(BKE_ptcache_object_reset(scene, ob, PTCACHE_RESET_OUTDATED)) + if(BKE_ptcache_object_reset(ob, PTCACHE_RESET_OUTDATED)) DAG_object_flush_update(scene, ob, OB_RECALC_DATA); } } @@ -1078,21 +584,12 @@ PointCache *BKE_ptcache_add() cache= MEM_callocN(sizeof(PointCache), "PointCache"); cache->startframe= 1; cache->endframe= 250; - cache->step= 10; return cache; } void BKE_ptcache_free(PointCache *cache) { - PTCacheMem *pm = cache->mem_cache.first; - if(pm) { - for(; pm; pm=pm->next) - MEM_freeN(pm->data); - - BLI_freelistN(&cache->mem_cache); - } - MEM_freeN(cache); } @@ -1108,276 +605,3 @@ PointCache *BKE_ptcache_copy(PointCache *cache) return ncache; } - - -/* Baking */ -static int count_quick_cache(Scene *scene, int *quick_step) -{ - Base *base = scene->base.first; - PTCacheID *pid; - ListBase pidlist; - int autocache_count= 0; - - for(base = scene->base.first; base; base = base->next) { - if(base->object) { - BKE_ptcache_ids_from_object(&pidlist, base->object); - - for(pid=pidlist.first; pid; pid=pid->next) { - if((pid->cache->flag & PTCACHE_BAKED) - || (pid->cache->flag & PTCACHE_QUICK_CACHE)==0) - continue; - - if(pid->cache->flag & PTCACHE_OUTDATED || (pid->cache->flag & PTCACHE_SIMULATION_VALID)==0) { - if(!autocache_count) - *quick_step = pid->cache->step; - else - *quick_step = MIN2(*quick_step, pid->cache->step); - - autocache_count++; - } - } - - BLI_freelistN(&pidlist); - } - } - - return autocache_count; -} -void BKE_ptcache_quick_cache_all(Scene *scene) -{ - PTCacheBaker baker; - - baker.bake=0; - baker.break_data=NULL; - baker.break_test=NULL; - baker.pid=NULL; - baker.progressbar=NULL; - baker.progresscontext=NULL; - baker.render=0; - baker.scene=scene; - - if(count_quick_cache(scene, &baker.quick_step)) - BKE_ptcache_make_cache(&baker); -} - -/* if bake is not given run simulations to current frame */ -void BKE_ptcache_make_cache(PTCacheBaker* baker) -{ - Scene *scene = baker->scene; - Base *base; - ListBase pidlist; - PTCacheID *pid = baker->pid; - PointCache *cache; - float frameleno = scene->r.framelen; - int cfrao = CFRA; - int startframe = MAXFRAME; - int endframe = CFRA; - int bake = baker->bake; - int render = baker->render; - int step = baker->quick_step; - - G.afbreek = 0; - - /* set caches to baking mode and figure out start frame */ - if(pid) { - /* cache/bake a single object */ - cache = pid->cache; - if((cache->flag & PTCACHE_BAKED)==0) { - if(pid->type==PTCACHE_TYPE_PARTICLES) - psys_get_pointcache_start_end(scene, pid->data, &cache->startframe, &cache->endframe); - - if(bake || cache->flag & PTCACHE_REDO_NEEDED) - BKE_ptcache_id_clear(pid, PTCACHE_CLEAR_ALL, 0); - - startframe = MAX2(cache->last_exact, cache->startframe); - - if(bake) { - endframe = cache->endframe; - cache->flag |= PTCACHE_BAKING; - } - else { - endframe = MIN2(endframe, cache->endframe); - } - - cache->flag &= ~PTCACHE_BAKED; - } - } - else for(base=scene->base.first; base; base= base->next) { - /* cache/bake everything in the scene */ - BKE_ptcache_ids_from_object(&pidlist, base->object); - - for(pid=pidlist.first; pid; pid=pid->next) { - cache = pid->cache; - if((cache->flag & PTCACHE_BAKED)==0) { - if(pid->type==PTCACHE_TYPE_PARTICLES) - psys_get_pointcache_start_end(scene, pid->data, &cache->startframe, &cache->endframe); - - if((cache->flag & PTCACHE_REDO_NEEDED || (cache->flag & PTCACHE_SIMULATION_VALID)==0) - && ((cache->flag & PTCACHE_QUICK_CACHE)==0 || render || bake)) - BKE_ptcache_id_clear(pid, PTCACHE_CLEAR_ALL, 0); - - startframe = MIN2(startframe, cache->startframe); - - if(bake || render) { - cache->flag |= PTCACHE_BAKING; - - if(bake) - endframe = MAX2(endframe, cache->endframe); - } - - cache->flag &= ~PTCACHE_BAKED; - - } - } - BLI_freelistN(&pidlist); - } - - CFRA= startframe; - scene->r.framelen = 1.0; - - for(; CFRA <= endframe; CFRA+=step) { - float prog; - - if(bake) - prog = (int)(100.0 * (float)(CFRA - startframe)/(float)(endframe-startframe)); - else - prog = CFRA; - - /* NOTE: baking should not redraw whole ui as this slows things down */ - if(baker->progressbar) - baker->progressbar(baker->progresscontext, prog); - - scene_update_for_newframe(scene, scene->lay); - - /* NOTE: breaking baking should leave calculated frames in cache, not clear it */ - if(baker->break_test && baker->break_test(baker->break_data)) - break; - } - - /* clear baking flag */ - if(pid) { - cache->flag &= ~(PTCACHE_BAKING|PTCACHE_REDO_NEEDED); - cache->flag |= PTCACHE_SIMULATION_VALID; - if(bake) - cache->flag |= PTCACHE_BAKED; - } - else for(base=scene->base.first; base; base= base->next) { - BKE_ptcache_ids_from_object(&pidlist, base->object); - - for(pid=pidlist.first; pid; pid=pid->next) { - cache = pid->cache; - - if(step > 1) - cache->flag &= ~(PTCACHE_BAKING|PTCACHE_OUTDATED); - else - cache->flag &= ~(PTCACHE_BAKING|PTCACHE_REDO_NEEDED); - - cache->flag |= PTCACHE_SIMULATION_VALID; - - if(bake) - cache->flag |= PTCACHE_BAKED; - } - BLI_freelistN(&pidlist); - } - - scene->r.framelen = frameleno; - CFRA = cfrao; - scene_update_for_newframe(scene, scene->lay); - - /* TODO: call redraw all windows somehow */ -} - -void BKE_ptcache_toggle_disk_cache(PTCacheID *pid) { - PointCache *cache = pid->cache; - PTCacheFile *pf; - PTCacheMem *pm; - int totelem=0; - int float_count=0; - int tot; - int last_exact = cache->last_exact; - - if (!G.relbase_valid){ - cache->flag &= ~PTCACHE_DISK_CACHE; - return; - } - - totelem = ptcache_pid_totelem(pid); - float_count = ptcache_pid_elemsize(pid) / sizeof(float); - - if(totelem==0 || float_count==0) - return; - - tot = totelem*float_count; - - /* MEM -> DISK */ - if(cache->flag & PTCACHE_DISK_CACHE) { - pm = cache->mem_cache.first; - - BKE_ptcache_id_clear(pid, PTCACHE_CLEAR_ALL, 0); - - for(; pm; pm=pm->next) { - pf = BKE_ptcache_file_open(pid, PTCACHE_FILE_WRITE, pm->frame); - - if(pf) { - if(fwrite(pm->data, sizeof(float), tot, pf->fp) != tot) { - printf("Error writing to disk cache\n"); - - cache->flag &= ~PTCACHE_DISK_CACHE; - - BKE_ptcache_file_close(pf); - return; - } - BKE_ptcache_file_close(pf); - } - else - printf("Error creating disk cache file\n"); - } - - cache->flag &= ~PTCACHE_DISK_CACHE; - BKE_ptcache_id_clear(pid, PTCACHE_CLEAR_ALL, 0); - cache->flag |= PTCACHE_DISK_CACHE; - } - /* DISK -> MEM */ - else { - int cfra; - int sfra = cache->startframe; - int efra = cache->endframe; - - BKE_ptcache_id_clear(pid, PTCACHE_CLEAR_ALL, 0); - - for(cfra=sfra; cfra <= efra; cfra++) { - pf = BKE_ptcache_file_open(pid, PTCACHE_FILE_READ, cfra); - - if(pf) { - pm = MEM_callocN(sizeof(PTCacheMem), "Pointcache mem"); - pm->data = MEM_callocN(sizeof(float)*tot, "Pointcache mem data"); - - if(fread(pm->data, sizeof(float), tot, pf->fp)!= tot) { - printf("Error reading from disk cache\n"); - - cache->flag |= PTCACHE_DISK_CACHE; - - MEM_freeN(pm->data); - MEM_freeN(pm); - BKE_ptcache_file_close(pf); - return; - } - - pm->frame = cfra; - pm->totpoint = totelem; - - BLI_addtail(&pid->cache->mem_cache, pm); - - BKE_ptcache_file_close(pf); - } - } - - cache->flag |= PTCACHE_DISK_CACHE; - BKE_ptcache_id_clear(pid, PTCACHE_CLEAR_ALL, 0); - cache->flag &= ~PTCACHE_DISK_CACHE; - } - - cache->last_exact = last_exact; - - BKE_ptcache_update_info(pid); -} diff --git a/source/blender/blenkernel/intern/report.c b/source/blender/blenkernel/intern/report.c index 116fd069948..1d97eccb9f3 100644 --- a/source/blender/blenkernel/intern/report.c +++ b/source/blender/blenkernel/intern/report.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: report.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenkernel/intern/scene.c b/source/blender/blenkernel/intern/scene.c index 23da5c66850..156bdae9b00 100644 --- a/source/blender/blenkernel/intern/scene.c +++ b/source/blender/blenkernel/intern/scene.c @@ -142,6 +142,8 @@ void free_scene(Scene *sce) BLI_freelistN(&sce->base); seq_free_editing(sce->ed); + if(sce->radio) MEM_freeN(sce->radio); + sce->radio= 0; #ifndef DISABLE_PYTHON BPY_free_scriptlink(&sce->scriptlink); @@ -203,6 +205,9 @@ Scene *add_scene(char *name) sce= alloc_libblock(&G.main->scene, ID_SCE, name); sce->lay= 1; + sce->selectmode= SCE_SELECT_VERTEX; + sce->editbutsize= 0.1; + sce->autokey_mode= U.autokey_mode; sce->r.mode= R_GAMMA; sce->r.cfra= 1; @@ -272,10 +277,6 @@ Scene *add_scene(char *name) sce->toolsettings->select_thresh= 0.01f; sce->toolsettings->jointrilimit = 0.8f; - sce->toolsettings->selectmode= SCE_SELECT_VERTEX; - sce->toolsettings->normalsize= 0.1; - sce->toolsettings->autokey_mode= U.autokey_mode; - sce->toolsettings->skgen_resolution = 100; sce->toolsettings->skgen_threshold_internal = 0.01f; sce->toolsettings->skgen_threshold_external = 0.01f; diff --git a/source/blender/blenkernel/intern/sequence.c b/source/blender/blenkernel/intern/sequence.c index 7fc262b4796..bb0665a5b0f 100644 --- a/source/blender/blenkernel/intern/sequence.c +++ b/source/blender/blenkernel/intern/sequence.c @@ -1,5 +1,5 @@ /** -* $Id$ +* $Id: sequence.c 17508 2008-11-20 00:34:24Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenlib/BLI_listbase.h b/source/blender/blenlib/BLI_listbase.h index d0b106b59c3..d2fb62141de 100644 --- a/source/blender/blenlib/BLI_listbase.h +++ b/source/blender/blenlib/BLI_listbase.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: BLI_blenlib.h 17433 2008-11-12 21:16:53Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -26,7 +26,7 @@ * * ***** END GPL LICENSE BLOCK ***** * - * $Id$ + * $Id: $ */ #ifndef BLI_LISTBASE_H diff --git a/source/blender/blenlib/BLI_noise.h b/source/blender/blenlib/BLI_noise.h index 0886eb3a8a5..9f72c5e7b54 100644 --- a/source/blender/blenlib/BLI_noise.h +++ b/source/blender/blenlib/BLI_noise.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: BLI_blenlib.h 17433 2008-11-12 21:16:53Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenlib/BLI_rect.h b/source/blender/blenlib/BLI_rect.h index c36a41af84b..c7026b21494 100644 --- a/source/blender/blenlib/BLI_rect.h +++ b/source/blender/blenlib/BLI_rect.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: BLI_blenlib.h 17433 2008-11-12 21:16:53Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenlib/BLI_storage.h b/source/blender/blenlib/BLI_storage.h index fa44bb36e15..d7bf3bd13f8 100644 --- a/source/blender/blenlib/BLI_storage.h +++ b/source/blender/blenlib/BLI_storage.h @@ -25,20 +25,15 @@ * * ***** END GPL LICENSE BLOCK ***** */ - #ifndef BLI_STORAGE_H #define BLI_STORAGE_H -/* NOTE: these have to be defined before including unistd.h! */ #ifndef __APPLE__ #ifndef WIN32 -#ifndef _LARGEFILE_SOURCE -#define _LARGEFILE_SOURCE -#define _LARGEFILE64_SOURCE +#define _LARGEFILE_SOURCE 1 #define _FILE_OFFSET_BITS 64 #endif #endif -#endif struct direntry; diff --git a/source/blender/blenlib/BLI_string.h b/source/blender/blenlib/BLI_string.h index bf93dc19cc5..4e5bf650196 100644 --- a/source/blender/blenlib/BLI_string.h +++ b/source/blender/blenlib/BLI_string.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: BLI_blenlib.h 17433 2008-11-12 21:16:53Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -26,7 +26,7 @@ * * ***** END GPL LICENSE BLOCK ***** * - * $Id$ + * $Id: $ */ #ifndef BLI_STRING_H diff --git a/source/blender/blenlib/intern/dynamiclist.c b/source/blender/blenlib/intern/dynamiclist.c index 4fe654cffb6..fbb87124bba 100644 --- a/source/blender/blenlib/intern/dynamiclist.c +++ b/source/blender/blenlib/intern/dynamiclist.c @@ -3,7 +3,7 @@ * various string, file, list operations. * * - * $Id$ + * $Id: util.c 17433 2008-11-12 21:16:53Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenlib/intern/dynamiclist.h b/source/blender/blenlib/intern/dynamiclist.h index e8c93fbcf23..aba3eda0696 100644 --- a/source/blender/blenlib/intern/dynamiclist.h +++ b/source/blender/blenlib/intern/dynamiclist.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BLI_dynamiclist.h 13161 2008-01-07 19:13:47Z hos $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenlib/intern/listbase.c b/source/blender/blenlib/intern/listbase.c index 1064c8ac1bf..e0fd5c37494 100644 --- a/source/blender/blenlib/intern/listbase.c +++ b/source/blender/blenlib/intern/listbase.c @@ -3,7 +3,7 @@ * various string, file, list operations. * * - * $Id$ + * $Id: util.c 17433 2008-11-12 21:16:53Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenlib/intern/psfont.c b/source/blender/blenlib/intern/psfont.c index 269e674a62f..39d38e4cf3a 100644 --- a/source/blender/blenlib/intern/psfont.c +++ b/source/blender/blenlib/intern/psfont.c @@ -837,7 +837,7 @@ static int decodetype1(PackedFile * pf, char *outname) while(newfgets(oneline, LINELEN, pf)) { hptr = (char *)oneline; while(*hptr) { - if(hextab[(int)*hptr] != NOTHEX) + if(hextab[*hptr] != NOTHEX) hexdat[hexbytes++] = *hptr; hptr++; } @@ -853,7 +853,7 @@ static int decodetype1(PackedFile * pf, char *outname) bptr = bindat; c = datbytes; while(c--) { - *bptr++ = (hextab[(int)hptr[0]]<<4)+hextab[(int)hptr[1]]; + *bptr++ = (hextab[hptr[0]]<<4)+hextab[hptr[1]]; hptr += 2; } diff --git a/source/blender/blenlib/intern/storage.c b/source/blender/blenlib/intern/storage.c index 0ae17a13e43..688a4ab901b 100644 --- a/source/blender/blenlib/intern/storage.c +++ b/source/blender/blenlib/intern/storage.c @@ -62,6 +62,13 @@ #include <sys/vfs.h> #endif +#ifdef __BeOS +struct statfs { + int f_bsize; + int f_bfree; +}; +#endif + #ifdef __APPLE__ /* For statfs */ #include <sys/param.h> @@ -70,7 +77,7 @@ #include <fcntl.h> -#if !defined(WIN32) +#if !defined(__BeOS) && !defined(WIN32) #include <sys/mtio.h> /* tape comando's */ #endif #include <string.h> /* strcpy etc.. */ @@ -194,6 +201,9 @@ double BLI_diskfree(char *dir) #if defined (__FreeBSD__) || defined (linux) || defined (__OpenBSD__) || defined (__APPLE__) if (statfs(name, &disk)) return(-1); #endif +#ifdef __BeOS + return -1; +#endif #if defined (__sun__) || defined (__sun) || defined (__sgi) if (statvfs(name, &disk)) return(-1); diff --git a/source/blender/blenlib/intern/string.c b/source/blender/blenlib/intern/string.c index 4cd04aa232c..fa4bcbc26bc 100644 --- a/source/blender/blenlib/intern/string.c +++ b/source/blender/blenlib/intern/string.c @@ -3,7 +3,7 @@ * various string, file, list operations. * * - * $Id$ + * $Id: util.c 17433 2008-11-12 21:16:53Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/blenlib/intern/util.c b/source/blender/blenlib/intern/util.c index 26f4c2dd415..df4ad4e7c75 100644 --- a/source/blender/blenlib/intern/util.c +++ b/source/blender/blenlib/intern/util.c @@ -737,7 +737,10 @@ void BLI_splitdirstring(char *di, char *fi) } char *BLI_gethome(void) { - #if !defined(WIN32) + #ifdef __BeOS + return "/boot/home/"; /* BeOS 4.5: doubleclick at icon doesnt give home env */ + + #elif !defined(WIN32) return getenv("HOME"); #else /* Windows */ diff --git a/source/blender/blenloader/intern/readblenentry.c b/source/blender/blenloader/intern/readblenentry.c index 1f276913ea8..0c8b8a6b31d 100644 --- a/source/blender/blenloader/intern/readblenentry.c +++ b/source/blender/blenloader/intern/readblenentry.c @@ -32,8 +32,6 @@ #include <config.h> #endif -#include "BLI_storage.h" /* _LARGEFILE_SOURCE */ - #include <stdlib.h> #include <string.h> #include <stdio.h> diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c index 441e8aff2d6..1502b475350 100644 --- a/source/blender/blenloader/intern/readfile.c +++ b/source/blender/blenloader/intern/readfile.c @@ -2878,16 +2878,6 @@ static void direct_link_material(FileData *fd, Material *ma) static void direct_link_pointcache(FileData *fd, PointCache *cache) { - if((cache->flag & PTCACHE_DISK_CACHE)==0) { - PTCacheMem *pm; - - link_list(fd, &cache->mem_cache); - - pm = cache->mem_cache.first; - - for(; pm; pm=pm->next) - pm->data = newdataadr(fd, pm->data); - } cache->flag &= ~(PTCACHE_SIMULATION_VALID|PTCACHE_BAKE_EDIT_ACTIVE); cache->simframe= 0; } @@ -2899,9 +2889,7 @@ static void lib_link_particlesettings(FileData *fd, Main *main) part= main->particle.first; while(part) { if(part->id.flag & LIB_NEEDLINK) { - if (part->adt) lib_link_animdata(fd, &part->id, part->adt); part->ipo= newlibadr_us(fd, part->id.lib, part->ipo); // XXX depreceated - old animation system - part->dup_ob = newlibadr(fd, part->id.lib, part->dup_ob); part->dup_group = newlibadr(fd, part->id.lib, part->dup_group); part->eff_group = newlibadr(fd, part->id.lib, part->eff_group); @@ -2914,7 +2902,6 @@ static void lib_link_particlesettings(FileData *fd, Main *main) static void direct_link_particlesettings(FileData *fd, ParticleSettings *part) { - part->adt= newdataadr(fd, part->adt); part->pd= newdataadr(fd, part->pd); part->pd2= newdataadr(fd, part->pd2); } @@ -3155,8 +3142,10 @@ static void direct_link_mesh(FileData *fd, Mesh *mesh) direct_link_dverts(fd, lvl->totvert, CustomData_get(&mesh->mr->vdata, 0, CD_MDEFORMVERT)); direct_link_customdata(fd, &mesh->mr->fdata, lvl->totface); - mesh->mr->edge_flags= newdataadr(fd, mesh->mr->edge_flags); - mesh->mr->edge_creases= newdataadr(fd, mesh->mr->edge_creases); + if(!mesh->mr->edge_flags) + mesh->mr->edge_flags= MEM_callocN(sizeof(short)*lvl->totedge, "Multires Edge Flags"); + if(!mesh->mr->edge_creases) + mesh->mr->edge_creases= MEM_callocN(sizeof(char)*lvl->totedge, "Multires Edge Creases"); mesh->mr->verts = newdataadr(fd, mesh->mr->verts); @@ -3944,6 +3933,8 @@ static void direct_link_scene(FileData *fd, Scene *sce) direct_link_keyingsets(fd, &sce->keyingsets); sce->basact= newdataadr(fd, sce->basact); + + sce->radio= newdataadr(fd, sce->radio); sce->toolsettings= newdataadr(fd, sce->toolsettings); if(sce->toolsettings) { @@ -7105,14 +7096,22 @@ static void do_versions(FileData *fd, Library *lib, Main *main) if(main->versionfile <= 234) { + Scene *sce; World *wo; bScreen *sc; + int set_zbuf_sel=0; // force sumo engine to be active for (wo = main->world.first; wo; wo= wo->id.next) { if(wo->physicsEngine==0) wo->physicsEngine = 2; } + for (sce= main->scene.first; sce; sce= sce->id.next) { + if(sce->selectmode==0) { + sce->selectmode= SCE_SELECT_VERTEX; + set_zbuf_sel= 1; + } + } for (sc= main->screen.first; sc; sc= sc->id.next) { ScrArea *sa; for (sa= sc->areabase.first; sa; sa= sa->next) { @@ -7120,7 +7119,7 @@ static void do_versions(FileData *fd, Library *lib, Main *main) for (sl= sa->spacedata.first; sl; sl= sl->next) { if(sl->spacetype==SPACE_VIEW3D) { View3D *v3d= (View3D *)sl; - v3d->flag |= V3D_ZBUF_SELECT; + if(set_zbuf_sel) v3d->flag |= V3D_ZBUF_SELECT; } else if(sl->spacetype==SPACE_TEXT) { SpaceText *st= (SpaceText *)sl; @@ -7155,10 +7154,16 @@ static void do_versions(FileData *fd, Library *lib, Main *main) } if(main->versionfile <= 236) { Object *ob; + Scene *sce= main->scene.first; Camera *cam= main->camera.first; Material *ma; bScreen *sc; + while(sce) { + if(sce->editbutsize==0.0) sce->editbutsize= 0.1f; + + sce= sce->id.next; + } while(cam) { if(cam->ortho_scale==0.0) { cam->ortho_scale= 256.0f/cam->lens; @@ -8784,6 +8789,15 @@ static void do_versions(FileData *fd, Library *lib, Main *main) } } } + /* autokey mode settings now used from scene, but need to be initialised off userprefs */ + if (main->versionfile < 247 || (main->versionfile == 247 && main->subversionfile < 8)) { + Scene *sce; + + for (sce= main->scene.first; sce; sce= sce->id.next) { + if (sce->autokey_mode == 0) + sce->autokey_mode= U.autokey_mode; + } + } if (main->versionfile < 247 || (main->versionfile == 247 && main->subversionfile < 9)) { Lamp *la= main->lamp.first; @@ -8976,34 +8990,6 @@ static void do_versions(FileData *fd, Library *lib, Main *main) } - if (main->versionfile < 249 && main->subversionfile < 2) { - Scene *sce= main->scene.first; - Sequence *seq; - Editing *ed; - - while(sce) { - ed= sce->ed; - if(ed) { - SEQP_BEGIN(ed, seq) { - if (seq->strip && seq->strip->proxy){ - if (sce->r.size != 100.0) { - seq->strip->proxy->size - = sce->r.size; - } else { - seq->strip->proxy->size - = 25.0; - } - seq->strip->proxy->quality =90; - } - } - SEQ_END - } - - sce= sce->id.next; - } - - } - if (main->versionfile < 250) { bScreen *screen; Scene *scene; @@ -9012,9 +8998,6 @@ static void do_versions(FileData *fd, Library *lib, Main *main) Scene *sce; Tex *tx; ParticleSettings *part; - Object *ob; - PTCacheID *pid; - ListBase pidlist; for(screen= main->screen.first; screen; screen= screen->id.next) { do_versions_windowmanager_2_50(screen); @@ -9057,7 +9040,7 @@ static void do_versions(FileData *fd, Library *lib, Main *main) me->drawflag= ME_DRAWEDGES|ME_DRAWFACES|ME_DRAWCREASES; } - /* particle draw and render types */ + /* particle settings conversion */ for(part= main->particle.first; part; part= part->id.next) { if(part->draw_as) { if(part->draw_as == PART_DRAW_DOT) { @@ -9073,16 +9056,6 @@ static void do_versions(FileData *fd, Library *lib, Main *main) } } } - /* set old pointcaches to have disk cache flag */ - for(ob = main->object.first; ob; ob= ob->id.next) { - - BKE_ptcache_ids_from_object(&pidlist, ob); - - for(pid=pidlist.first; pid; pid=pid->next) - pid->cache->flag |= PTCACHE_DISK_CACHE; - - BLI_freelistN(&pidlist); - } } /* TODO: should be moved into one of the version blocks once this branch moves to trunk and we can @@ -9090,8 +9063,6 @@ static void do_versions(FileData *fd, Library *lib, Main *main) { Object *ob; Material *ma; - Scene *sce; - ToolSettings *ts; int i; for(ob = main->object.first; ob; ob = ob->id.next) { @@ -9164,17 +9135,37 @@ static void do_versions(FileData *fd, Library *lib, Main *main) ma->mode &= ~MA_HALO; } } - - for(sce = main->scene.first; sce; sce = sce->id.next) { - ts= sce->toolsettings; - if(ts->normalsize == 0.0) { - ts->normalsize= 0.1f; - ts->selectmode= SCE_SELECT_VERTEX; - ts->autokey_mode= U.autokey_mode; + } + + if (main->versionfile < 249 && main->subversionfile < 2) { + Scene *sce= main->scene.first; + Sequence *seq; + Editing *ed; + + while(sce) { + ed= sce->ed; + if(ed) { + SEQP_BEGIN(ed, seq) { + if (seq->strip && seq->strip->proxy){ + if (sce->r.size != 100.0) { + seq->strip->proxy->size + = sce->r.size; + } else { + seq->strip->proxy->size + = 25.0; + } + seq->strip->proxy->quality =90; + } + } + SEQ_END } + + sce= sce->id.next; } + } + /* WATCH IT!!!: pointers from libdata have not been converted yet here! */ /* WATCH IT 2!: Userdef struct init has to be in src/usiblender.c! */ @@ -9526,8 +9517,6 @@ static void expand_particlesettings(FileData *fd, Main *mainvar, ParticleSetting expand_doit(fd, mainvar, part->dup_group); expand_doit(fd, mainvar, part->eff_group); expand_doit(fd, mainvar, part->bb_ob); - - expand_animdata(fd, mainvar, part->adt); } static void expand_group(FileData *fd, Main *mainvar, Group *group) diff --git a/source/blender/blenloader/intern/writefile.c b/source/blender/blenloader/intern/writefile.c index c433232d084..f8112406e80 100644 --- a/source/blender/blenloader/intern/writefile.c +++ b/source/blender/blenloader/intern/writefile.c @@ -382,7 +382,6 @@ static void writedata(WriteData *wd, int filecode, int len, void *adr) /* do not /*These functions are used by blender's .blend system for file saving/loading.*/ void IDP_WriteProperty_OnlyData(IDProperty *prop, void *wd); void IDP_WriteProperty(IDProperty *prop, void *wd); -static void write_animdata(WriteData *wd, AnimData *adt); // XXX code needs reshuffling, but not before NLA SoC is merged back into 2.5 static void IDP_WriteArray(IDProperty *prop, void *wd) { @@ -550,25 +549,6 @@ static void write_userdef(WriteData *wd) } } -/* TODO: replace *cache with *cachelist once it's coded */ -#define PTCACHE_WRITE_PSYS 0 -#define PTCACHE_WRITE_CLOTH 1 -static void write_pointcaches(WriteData *wd, PointCache *cache, int type) -{ - writestruct(wd, DATA, "PointCache", 1, cache); - - if((cache->flag & PTCACHE_DISK_CACHE)==0) { - PTCacheMem *pm = cache->mem_cache.first; - - for(; pm; pm=pm->next) { - writestruct(wd, DATA, "PTCacheMem", 1, pm); - if(type==PTCACHE_WRITE_PSYS) - writestruct(wd, DATA, "ParticleKey", pm->totpoint, pm->data); - else if(type==PTCACHE_WRITE_CLOTH) - writedata(wd, DATA, 9 * sizeof(float) * pm->totpoint, pm->data); - } - } -} static void write_particlesettings(WriteData *wd, ListBase *idbase) { ParticleSettings *part; @@ -579,7 +559,6 @@ static void write_particlesettings(WriteData *wd, ListBase *idbase) /* write LibData */ writestruct(wd, ID_PA, "ParticleSettings", 1, part); if (part->id.properties) IDP_WriteProperty(part->id.properties, wd); - if (part->adt) write_animdata(wd, part->adt); writestruct(wd, DATA, "PartDeflect", 1, part->pd); writestruct(wd, DATA, "PartDeflect", 1, part->pd2); } @@ -606,8 +585,8 @@ static void write_particlesystems(WriteData *wd, ListBase *particles) } if(psys->child) writestruct(wd, DATA, "ChildParticle", psys->totchild ,psys->child); writestruct(wd, DATA, "SoftBody", 1, psys->soft); - if(psys->soft) write_pointcaches(wd, psys->soft->pointcache, PTCACHE_WRITE_PSYS); - write_pointcaches(wd, psys->pointcache, PTCACHE_WRITE_PSYS); + if(psys->soft) writestruct(wd, DATA, "PointCache", 1, psys->soft->pointcache); + writestruct(wd, DATA, "PointCache", 1, psys->pointcache); } } @@ -1028,7 +1007,7 @@ static void write_modifiers(WriteData *wd, ListBase *modbase, int write_undo) writestruct(wd, DATA, "ClothSimSettings", 1, clmd->sim_parms); writestruct(wd, DATA, "ClothCollSettings", 1, clmd->coll_parms); - write_pointcaches(wd, clmd->point_cache, PTCACHE_WRITE_CLOTH); + writestruct(wd, DATA, "PointCache", 1, clmd->point_cache); } else if(md->type==eModifierType_Fluidsim) { FluidsimModifierData *fluidmd = (FluidsimModifierData*) md; @@ -1605,6 +1584,7 @@ static void write_scenes(WriteData *wd, ListBase *scebase) base= base->next; } + writestruct(wd, DATA, "Radio", 1, sce->radio); writestruct(wd, DATA, "ToolSettings", 1, sce->toolsettings); if(sce->toolsettings->vpaint) writestruct(wd, DATA, "VPaint", 1, sce->toolsettings->vpaint); diff --git a/source/blender/blenpluginapi/intern/Makefile b/source/blender/blenpluginapi/intern/Makefile index 20a61e9a25c..51905cad8ec 100644 --- a/source/blender/blenpluginapi/intern/Makefile +++ b/source/blender/blenpluginapi/intern/Makefile @@ -33,6 +33,10 @@ DIR = $(OCGDIR)/blender/$(LIBNAME) include nan_compile.mk +ifeq ($(OS),$(findstring $(OS), "beos darwin freebsd linux openbsd solaris")) + CFLAGS += -shared +endif + CFLAGS += $(LEVEL_1_C_WARNINGS) # path to our own external headerfiles. On win2k this needs to be diff --git a/source/blender/editors/animation/Makefile b/source/blender/editors/animation/Makefile index a7f36aa58ac..19b62891b63 100644 --- a/source/blender/editors/animation/Makefile +++ b/source/blender/editors/animation/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/animation/anim_channels.c b/source/blender/editors/animation/anim_channels.c index 05d50f98e8e..c52ade1bba8 100644 --- a/source/blender/editors/animation/anim_channels.c +++ b/source/blender/editors/animation/anim_channels.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: editaction.c 17746 2008-12-08 11:19:44Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/animation/keyframes_draw.c b/source/blender/editors/animation/keyframes_draw.c index d0e83eeaec7..cfbd6d2bced 100644 --- a/source/blender/editors/animation/keyframes_draw.c +++ b/source/blender/editors/animation/keyframes_draw.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: drawaction.c 17746 2008-12-08 11:19:44Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/armature/BIF_generate.h b/source/blender/editors/armature/BIF_generate.h index bde079c45fb..2d46cfa41e6 100644 --- a/source/blender/editors/armature/BIF_generate.h +++ b/source/blender/editors/armature/BIF_generate.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BIF_generate.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/armature/BIF_retarget.h b/source/blender/editors/armature/BIF_retarget.h index c39f410424a..56f7e4cdd5d 100644 --- a/source/blender/editors/armature/BIF_retarget.h +++ b/source/blender/editors/armature/BIF_retarget.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BIF_retarget.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/armature/Makefile b/source/blender/editors/armature/Makefile index 0291bcb1830..6c7ce81a8a1 100644 --- a/source/blender/editors/armature/Makefile +++ b/source/blender/editors/armature/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/armature/editarmature_generate.c b/source/blender/editors/armature/editarmature_generate.c index 6d271375c64..a50f767cf14 100644 --- a/source/blender/editors/armature/editarmature_generate.c +++ b/source/blender/editors/armature/editarmature_generate.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: editarmature_generate.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/armature/editarmature_sketch.c b/source/blender/editors/armature/editarmature_sketch.c index fb030b91ce1..1b879569e9c 100644 --- a/source/blender/editors/armature/editarmature_sketch.c +++ b/source/blender/editors/armature/editarmature_sketch.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: editarmature_sketch.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -243,7 +243,6 @@ void BIF_makeListTemplates(bContext *C) { Object *obedit = CTX_data_edit_object(C); Scene *scene = CTX_data_scene(C); - ToolSettings *ts = CTX_data_tool_settings(C); Base *base; int index = 0; @@ -264,7 +263,7 @@ void BIF_makeListTemplates(bContext *C) index++; BLI_ghash_insert(TEMPLATES_HASH, SET_INT_IN_POINTER(index), ob); - if (ob == ts->skgen_template) + if (ob == scene->toolsettings->skgen_template) { TEMPLATES_CURRENT = index; } @@ -306,9 +305,8 @@ char *BIF_listTemplates(bContext *C) int BIF_currentTemplate(bContext *C) { - ToolSettings *ts = CTX_data_tool_settings(C); - - if (TEMPLATES_CURRENT == 0 && ts->skgen_template != NULL) + Scene *scene = CTX_data_scene(C); + if (TEMPLATES_CURRENT == 0 && scene->toolsettings->skgen_template != NULL) { GHashIterator ghi; BLI_ghashIterator_init(&ghi, TEMPLATES_HASH); @@ -318,7 +316,7 @@ int BIF_currentTemplate(bContext *C) Object *ob = BLI_ghashIterator_getValue(&ghi); int key = GET_INT_FROM_POINTER(BLI_ghashIterator_getKey(&ghi)); - if (ob == ts->skgen_template) + if (ob == scene->toolsettings->skgen_template) { TEMPLATES_CURRENT = key; break; @@ -362,8 +360,8 @@ RigGraph* sk_makeTemplateGraph(bContext *C, Object *ob) int BIF_nbJointsTemplate(bContext *C) { - ToolSettings *ts = CTX_data_tool_settings(C); - RigGraph *rg = sk_makeTemplateGraph(C, ts->skgen_template); + Scene *scene = CTX_data_scene(C); + RigGraph *rg = sk_makeTemplateGraph(C, scene->toolsettings->skgen_template); if (rg) { @@ -377,7 +375,7 @@ int BIF_nbJointsTemplate(bContext *C) char * BIF_nameBoneTemplate(bContext *C) { - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); SK_Sketch *stk = GLOBAL_sketch; RigGraph *rg; int index = 0; @@ -387,7 +385,7 @@ char * BIF_nameBoneTemplate(bContext *C) index = stk->active_stroke->nb_points; } - rg = sk_makeTemplateGraph(C, ts->skgen_template); + rg = sk_makeTemplateGraph(C, scene->toolsettings->skgen_template); if (rg == NULL) { @@ -420,14 +418,14 @@ void BIF_freeTemplates(bContext *C) void BIF_setTemplate(bContext *C, int index) { - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); if (index > 0) { - ts->skgen_template = BLI_ghash_lookup(TEMPLATES_HASH, SET_INT_IN_POINTER(index)); + scene->toolsettings->skgen_template = BLI_ghash_lookup(TEMPLATES_HASH, SET_INT_IN_POINTER(index)); } else { - ts->skgen_template = NULL; + scene->toolsettings->skgen_template = NULL; if (TEMPLATE_RIGG != NULL) { @@ -441,19 +439,19 @@ void BIF_setTemplate(bContext *C, int index) void sk_autoname(bContext *C, ReebArc *arc) { - ToolSettings *ts = CTX_data_tool_settings(C); - if (ts->skgen_retarget_options & SK_RETARGET_AUTONAME) + Scene *scene = CTX_data_scene(C); + if (scene->toolsettings->skgen_retarget_options & SK_RETARGET_AUTONAME) { if (arc == NULL) { - char *num = ts->skgen_num_string; + char *num = scene->toolsettings->skgen_num_string; int i = atoi(num); i++; BLI_snprintf(num, 8, "%i", i); } else { - char *side = ts->skgen_side_string; + char *side = scene->toolsettings->skgen_side_string; int valid = 0; int caps = 0; @@ -527,7 +525,7 @@ ReebArc *sk_strokeToArc(SK_Stroke *stk, float imat[][4], float tmat[][3]) void sk_retargetStroke(bContext *C, SK_Stroke *stk) { - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); Object *obedit = CTX_data_edit_object(C); float imat[4][4]; float tmat[3][3]; @@ -543,7 +541,7 @@ void sk_retargetStroke(bContext *C, SK_Stroke *stk) sk_autoname(C, arc); - rg = sk_makeTemplateGraph(C, ts->skgen_template); + rg = sk_makeTemplateGraph(C, scene->toolsettings->skgen_template); BIF_retargetArc(C, arc, rg); @@ -1410,10 +1408,10 @@ void sk_startStroke(SK_Sketch *sketch) void sk_endStroke(bContext *C, SK_Sketch *sketch) { - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); sk_shrinkStrokeBuffer(sketch->active_stroke); - if (ts->bone_sketching & BONE_SKETCHING_ADJUST) + if (scene->toolsettings->bone_sketching & BONE_SKETCHING_ADJUST) { sk_endOverdraw(sketch); } @@ -1523,10 +1521,10 @@ int sk_addStrokeDrawPoint(bContext *C, SK_Sketch *sketch, SK_Stroke *stk, SK_Dra int sk_getStrokeSnapPoint(bContext *C, SK_Point *pt, SK_Sketch *sketch, SK_Stroke *stk, SK_DrawData *dd) { - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); int point_added = 0; - if (ts->snap_mode == SCE_SNAP_MODE_VOLUME) + if (scene->snap_mode == SCE_SNAP_MODE_VOLUME) { ListBase depth_peels; DepthPeel *p1, *p2; @@ -1559,7 +1557,7 @@ int sk_getStrokeSnapPoint(bContext *C, SK_Point *pt, SK_Sketch *sketch, SK_Strok p1->flag = 1; /* if peeling objects, take the first and last from each object */ - if (ts->snap_flag & SCE_SNAP_PEEL_OBJECT) + if (scene->snap_flag & SCE_SNAP_PEEL_OBJECT) { DepthPeel *peel; for (peel = p1->next; peel; peel = peel->next) @@ -1629,7 +1627,7 @@ int sk_getStrokeSnapPoint(bContext *C, SK_Point *pt, SK_Sketch *sketch, SK_Strok int dist = SNAP_MIN_DISTANCE; // Use a user defined value here /* snap to strokes */ - // if (ts->snap_mode == SCE_SNAP_MODE_VERTEX) /* snap all the time to strokes */ + // if (scene->snap_mode == SCE_SNAP_MODE_VERTEX) /* snap all the time to strokes */ for (snap_stk = sketch->strokes.first; snap_stk; snap_stk = snap_stk->next) { SK_Point *spt = NULL; @@ -1715,7 +1713,7 @@ int sk_addStrokeSnapPoint(bContext *C, SK_Sketch *sketch, SK_Stroke *stk, SK_Dra void sk_addStrokePoint(bContext *C, SK_Sketch *sketch, SK_Stroke *stk, SK_DrawData *dd, short snap) { - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); int point_added = 0; if (snap) @@ -1728,7 +1726,7 @@ void sk_addStrokePoint(bContext *C, SK_Sketch *sketch, SK_Stroke *stk, SK_DrawDa point_added = sk_addStrokeDrawPoint(C, sketch, stk, dd); } - if (stk == sketch->active_stroke && ts->bone_sketching & BONE_SKETCHING_ADJUST) + if (stk == sketch->active_stroke && scene->toolsettings->bone_sketching & BONE_SKETCHING_ADJUST) { sk_updateOverdraw(C, sketch, stk, dd); } @@ -1953,7 +1951,7 @@ static int iteratorStopped(void *arg) void sk_convertStroke(bContext *C, SK_Stroke *stk) { Object *obedit = CTX_data_edit_object(C); - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); bArmature *arm = obedit->data; SK_Point *head; EditBone *parent = NULL; @@ -1992,17 +1990,17 @@ void sk_convertStroke(bContext *C, SK_Stroke *stk) initStrokeIterator(iter, stk, head_index, i); - if (ts->bone_sketching_convert == SK_CONVERT_CUT_ADAPTATIVE) + if (scene->toolsettings->bone_sketching_convert == SK_CONVERT_CUT_ADAPTATIVE) { - bone = subdivideArcBy(ts, arm, arm->edbo, iter, invmat, tmat, nextAdaptativeSubdivision); + bone = subdivideArcBy(scene->toolsettings, arm, arm->edbo, iter, invmat, tmat, nextAdaptativeSubdivision); } - else if (ts->bone_sketching_convert == SK_CONVERT_CUT_LENGTH) + else if (scene->toolsettings->bone_sketching_convert == SK_CONVERT_CUT_LENGTH) { - bone = subdivideArcBy(ts, arm, arm->edbo, iter, invmat, tmat, nextLengthSubdivision); + bone = subdivideArcBy(scene->toolsettings, arm, arm->edbo, iter, invmat, tmat, nextLengthSubdivision); } - else if (ts->bone_sketching_convert == SK_CONVERT_CUT_FIXED) + else if (scene->toolsettings->bone_sketching_convert == SK_CONVERT_CUT_FIXED) { - bone = subdivideArcBy(ts, arm, arm->edbo, iter, invmat, tmat, nextFixedSubdivision); + bone = subdivideArcBy(scene->toolsettings, arm, arm->edbo, iter, invmat, tmat, nextFixedSubdivision); } } @@ -2044,14 +2042,14 @@ void sk_convertStroke(bContext *C, SK_Stroke *stk) void sk_convert(bContext *C, SK_Sketch *sketch) { - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); SK_Stroke *stk; for (stk = sketch->strokes.first; stk; stk = stk->next) { if (stk->selected == 1) { - if (ts->bone_sketching_convert == SK_CONVERT_RETARGET) + if (scene->toolsettings->bone_sketching_convert == SK_CONVERT_RETARGET) { sk_retargetStroke(C, stk); } @@ -2695,7 +2693,7 @@ void sk_selectStroke(bContext *C, SK_Sketch *sketch, short mval[2], int extend) rect.ymin= mval[1]-5; rect.ymax= mval[1]+5; - hits = view3d_opengl_select(&vc, buffer, MAXPICKBUF, &rect); + hits= view3d_opengl_select(&vc, buffer, MAXPICKBUF, &rect); if (hits>0) { @@ -2745,7 +2743,6 @@ void sk_queueRedrawSketch(SK_Sketch *sketch) void sk_drawSketch(Scene *scene, SK_Sketch *sketch, int with_names) { - ToolSettings *ts= scene->toolsettings; SK_Stroke *stk; glDisable(GL_DEPTH_TEST); @@ -2782,7 +2779,7 @@ void sk_drawSketch(Scene *scene, SK_Sketch *sketch, int with_names) if (stk->selected == 1) { - sk_drawStrokeSubdivision(ts, stk); + sk_drawStrokeSubdivision(scene->toolsettings, stk); } } @@ -2797,9 +2794,9 @@ void sk_drawSketch(Scene *scene, SK_Sketch *sketch, int with_names) { SK_Point *last = sk_lastStrokePoint(sketch->active_stroke); - if (ts->bone_sketching & BONE_SKETCHING_QUICK) + if (scene->toolsettings->bone_sketching & BONE_SKETCHING_QUICK) { - sk_drawStrokeSubdivision(ts, sketch->active_stroke); + sk_drawStrokeSubdivision(scene->toolsettings, sketch->active_stroke); } if (last != NULL) @@ -2842,7 +2839,7 @@ void sk_drawSketch(Scene *scene, SK_Sketch *sketch, int with_names) int sk_finish_stroke(bContext *C, SK_Sketch *sketch) { - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); if (sketch->active_stroke != NULL) { @@ -2850,9 +2847,9 @@ int sk_finish_stroke(bContext *C, SK_Sketch *sketch) sk_endStroke(C, sketch); - if (ts->bone_sketching & BONE_SKETCHING_QUICK) + if (scene->toolsettings->bone_sketching & BONE_SKETCHING_QUICK) { - if (ts->bone_sketching_convert == SK_CONVERT_RETARGET) + if (scene->toolsettings->bone_sketching_convert == SK_CONVERT_RETARGET) { sk_retargetStroke(C, stk); } @@ -3199,11 +3196,11 @@ static int sketch_draw_preview(bContext *C, wmOperator *op, wmEvent *event) int ED_operator_sketch_mode_active_stroke(bContext *C) { Object *obedit = CTX_data_edit_object(C); - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); if (obedit && obedit->type == OB_ARMATURE && - ts->bone_sketching & BONE_SKETCHING && + scene->toolsettings->bone_sketching & BONE_SKETCHING && GLOBAL_sketch != NULL && GLOBAL_sketch->active_stroke != NULL) { @@ -3218,12 +3215,12 @@ int ED_operator_sketch_mode_active_stroke(bContext *C) int ED_operator_sketch_mode_gesture(bContext *C) { Object *obedit = CTX_data_edit_object(C); - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); if (obedit && obedit->type == OB_ARMATURE && - ts->bone_sketching & BONE_SKETCHING && - (ts->bone_sketching & BONE_SKETCHING_QUICK) == 0 && + scene->toolsettings->bone_sketching & BONE_SKETCHING && + (scene->toolsettings->bone_sketching & BONE_SKETCHING_QUICK) == 0 && GLOBAL_sketch != NULL && GLOBAL_sketch->active_stroke == NULL) { @@ -3238,12 +3235,12 @@ int ED_operator_sketch_mode_gesture(bContext *C) int ED_operator_sketch_full_mode(bContext *C) { Object *obedit = CTX_data_edit_object(C); - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); if (obedit && obedit->type == OB_ARMATURE && - ts->bone_sketching & BONE_SKETCHING && - (ts->bone_sketching & BONE_SKETCHING_QUICK) == 0) + scene->toolsettings->bone_sketching & BONE_SKETCHING && + (scene->toolsettings->bone_sketching & BONE_SKETCHING_QUICK) == 0) { return 1; } @@ -3256,11 +3253,11 @@ int ED_operator_sketch_full_mode(bContext *C) int ED_operator_sketch_mode(bContext *C) { Object *obedit = CTX_data_edit_object(C); - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); if (obedit && obedit->type == OB_ARMATURE && - ts->bone_sketching & BONE_SKETCHING) + scene->toolsettings->bone_sketching & BONE_SKETCHING) { return 1; } diff --git a/source/blender/editors/armature/meshlaplacian.c b/source/blender/editors/armature/meshlaplacian.c index d74c8dbd0e1..4a0ee474f25 100644 --- a/source/blender/editors/armature/meshlaplacian.c +++ b/source/blender/editors/armature/meshlaplacian.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: meshlaplacian.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/armature/meshlaplacian.h b/source/blender/editors/armature/meshlaplacian.h index 00c0aefaec7..ff921e93909 100644 --- a/source/blender/editors/armature/meshlaplacian.h +++ b/source/blender/editors/armature/meshlaplacian.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: meshlaplacian.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/curve/Makefile b/source/blender/editors/curve/Makefile index 6449700e50b..6b1f628f231 100644 --- a/source/blender/editors/curve/Makefile +++ b/source/blender/editors/curve/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/curve/curve_intern.h b/source/blender/editors/curve/curve_intern.h index 2146855a75e..a73a54323ee 100644 --- a/source/blender/editors/curve/curve_intern.h +++ b/source/blender/editors/curve/curve_intern.h @@ -49,6 +49,7 @@ void FONT_OT_case_toggle(struct wmOperatorType *ot); void FONT_OT_case_set(struct wmOperatorType *ot); void FONT_OT_style_toggle(struct wmOperatorType *ot); void FONT_OT_style_set(struct wmOperatorType *ot); +void FONT_OT_material_set(struct wmOperatorType *ot); void FONT_OT_text_copy(struct wmOperatorType *ot); void FONT_OT_text_cut(struct wmOperatorType *ot); diff --git a/source/blender/editors/curve/curve_ops.c b/source/blender/editors/curve/curve_ops.c index 66cde772f3e..5292d86d3c9 100644 --- a/source/blender/editors/curve/curve_ops.c +++ b/source/blender/editors/curve/curve_ops.c @@ -106,6 +106,7 @@ void ED_operatortypes_curve(void) WM_operatortype_append(FONT_OT_case_set); WM_operatortype_append(FONT_OT_style_toggle); WM_operatortype_append(FONT_OT_style_set); + WM_operatortype_append(FONT_OT_material_set); WM_operatortype_append(FONT_OT_text_copy); WM_operatortype_append(FONT_OT_text_cut); diff --git a/source/blender/editors/curve/editcurve.c b/source/blender/editors/curve/editcurve.c index 5283aacf39e..466908c562c 100644 --- a/source/blender/editors/curve/editcurve.c +++ b/source/blender/editors/curve/editcurve.c @@ -189,7 +189,7 @@ static short swap_selection_bpoint(BPoint *bp) return select_bpoint(bp, SELECT, 1, VISIBLE); } -int isNurbsel(Nurb *nu) +short isNurbsel(Nurb *nu) { BezTriple *bezt; BPoint *bp; diff --git a/source/blender/editors/curve/editfont.c b/source/blender/editors/curve/editfont.c index 9f2bd6f26f9..5389db9e2ee 100644 --- a/source/blender/editors/curve/editfont.c +++ b/source/blender/editors/curve/editfont.c @@ -700,6 +700,50 @@ void FONT_OT_style_toggle(wmOperatorType *ot) RNA_def_enum(ot->srna, "style", style_items, CU_BOLD, "Style", "Style to set selection to."); } +/******************* set material operator ********************/ + +static int set_material_exec(bContext *C, wmOperator *op) +{ + Scene *scene= CTX_data_scene(C); + Object *obedit= CTX_data_edit_object(C); + Curve *cu= obedit->data; + EditFont *ef= cu->editfont; + int i, mat_nr, selstart, selend; + + if(!BKE_font_getselection(obedit, &selstart, &selend)) + return OPERATOR_CANCELLED; + + if(RNA_property_is_set(op->ptr, "index")) + mat_nr= RNA_int_get(op->ptr, "index"); + else + mat_nr= obedit->actcol; + + for(i=selstart; i<=selend; i++) + ef->textbufinfo[i].mat_nr = mat_nr; + + DAG_object_flush_update(scene, obedit, OB_RECALC_DATA); + WM_event_add_notifier(C, NC_OBJECT|ND_GEOM_DATA, obedit); + + return OPERATOR_FINISHED; +} + +void FONT_OT_material_set(wmOperatorType *ot) +{ + /* identifiers */ + ot->name= "Set Material"; + ot->idname= "FONT_OT_material_set"; + + /* api callbacks */ + ot->exec= set_material_exec; + ot->poll= ED_operator_editfont; + + /* flags */ + ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + + /* properties */ + RNA_def_int(ot->srna, "index", 0, 0, INT_MAX, "Material Index", "Material slot index.", 0, INT_MAX); +} + /******************* copy text operator ********************/ static void copy_selection(Object *obedit) diff --git a/source/blender/editors/datafiles/Bfont.c b/source/blender/editors/datafiles/Bfont.c index cd45debcbe4..4080a0d369f 100644 --- a/source/blender/editors/datafiles/Bfont.c +++ b/source/blender/editors/datafiles/Bfont.c @@ -1,6 +1,6 @@ /* DataToC output of file <Bfont> */ /* - * $Id$ + * $Id: Bfont.c 125 2002-11-25 12:02:15Z mein $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/datafiles/Makefile b/source/blender/editors/datafiles/Makefile index d7bb4e7222f..4162125623e 100644 --- a/source/blender/editors/datafiles/Makefile +++ b/source/blender/editors/datafiles/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/gpencil/Makefile b/source/blender/editors/gpencil/Makefile index 9bc5f491a83..f4c1cd246f4 100644 --- a/source/blender/editors/gpencil/Makefile +++ b/source/blender/editors/gpencil/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/gpencil/gpencil_edit.c b/source/blender/editors/gpencil/gpencil_edit.c index c0c1cbc7ac6..bad86c170ab 100644 --- a/source/blender/editors/gpencil/gpencil_edit.c +++ b/source/blender/editors/gpencil/gpencil_edit.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: gpencil.c 19758 2009-04-16 13:10:08Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/include/BIF_gl.h b/source/blender/editors/include/BIF_gl.h index c1b3b056d62..014201648c9 100644 --- a/source/blender/editors/include/BIF_gl.h +++ b/source/blender/editors/include/BIF_gl.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BIF_gl.h 10455 2007-04-04 13:18:41Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/include/ED_curve.h b/source/blender/editors/include/ED_curve.h index 2cebc6a572a..c619ee80f70 100644 --- a/source/blender/editors/include/ED_curve.h +++ b/source/blender/editors/include/ED_curve.h @@ -30,7 +30,6 @@ struct Base; struct bContext; -struct Nurb; struct Object; struct Scene; struct Text; @@ -53,8 +52,6 @@ void mouse_nurb (struct bContext *C, short mval[2], int extend); struct Nurb *add_nurbs_primitive(struct bContext *C, int type, int newname); -int isNurbsel (struct Nurb *nu);; - /* editfont.h */ void undo_push_font (struct bContext *C, char *name); void make_editText (struct Object *obedit); diff --git a/source/blender/editors/include/ED_datafiles.h b/source/blender/editors/include/ED_datafiles.h index 5d24b93418b..c1802c2952b 100644 --- a/source/blender/editors/include/ED_datafiles.h +++ b/source/blender/editors/include/ED_datafiles.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: ED_datafiles.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/include/ED_fluidsim.h b/source/blender/editors/include/ED_fluidsim.h index 586f16f42aa..bda879173c3 100644 --- a/source/blender/editors/include/ED_fluidsim.h +++ b/source/blender/editors/include/ED_fluidsim.h @@ -1,7 +1,7 @@ /** * BKE_fluidsim.h * - * $Id$ + * $Id: LBM_fluidsim.h 17433 2008-11-12 21:16:53Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/include/ED_keyframes_draw.h b/source/blender/editors/include/ED_keyframes_draw.h index e104bce90f6..81420ac95e5 100644 --- a/source/blender/editors/include/ED_keyframes_draw.h +++ b/source/blender/editors/include/ED_keyframes_draw.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BDR_drawaction.h 17579 2008-11-26 11:01:56Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/include/ED_keyframing.h b/source/blender/editors/include/ED_keyframing.h index 9d063910aa9..fbb469f8d43 100644 --- a/source/blender/editors/include/ED_keyframing.h +++ b/source/blender/editors/include/ED_keyframing.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BIF_keyframing.h 17216 2008-10-29 11:20:02Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -178,9 +178,9 @@ void ANIM_OT_remove_driver_button(struct wmOperatorType *ot); /* Auto-Keying macros for use by various tools */ /* check if auto-keyframing is enabled (per scene takes presidence) */ -#define IS_AUTOKEY_ON(scene) ((scene) ? (scene->toolsettings->autokey_mode & AUTOKEY_ON) : (U.autokey_mode & AUTOKEY_ON)) +#define IS_AUTOKEY_ON(scene) ((scene) ? (scene->autokey_mode & AUTOKEY_ON) : (U.autokey_mode & AUTOKEY_ON)) /* check the mode for auto-keyframing (per scene takes presidence) */ -#define IS_AUTOKEY_MODE(scene, mode) ((scene) ? (scene->toolsettings->autokey_mode == AUTOKEY_MODE_##mode) : (U.autokey_mode == AUTOKEY_MODE_##mode)) +#define IS_AUTOKEY_MODE(scene, mode) ((scene) ? (scene->autokey_mode == AUTOKEY_MODE_##mode) : (U.autokey_mode == AUTOKEY_MODE_##mode)) /* check if a flag is set for auto-keyframing (as userprefs only!) */ #define IS_AUTOKEY_FLAG(flag) (U.autokey_flag & AUTOKEY_FLAG_##flag) diff --git a/source/blender/editors/include/ED_mesh.h b/source/blender/editors/include/ED_mesh.h index 937f6384f6a..6dff4ee6ca4 100644 --- a/source/blender/editors/include/ED_mesh.h +++ b/source/blender/editors/include/ED_mesh.h @@ -147,9 +147,6 @@ int EM_init_backbuf_circle(struct ViewContext *vc, short xs, short ys, short r void EM_hide_mesh(struct EditMesh *em, int swap); void EM_reveal_mesh(struct EditMesh *em); -void EM_select_by_material(struct EditMesh *em, int index); -void EM_deselect_by_material(struct EditMesh *em, int index); - /* editface.c */ struct MTFace *EM_get_active_mtface(struct EditMesh *em, struct EditFace **act_efa, struct MCol **mcol, int sloppy); diff --git a/source/blender/editors/include/ED_object.h b/source/blender/editors/include/ED_object.h index e4e4b1d0486..bfa819632c9 100644 --- a/source/blender/editors/include/ED_object.h +++ b/source/blender/editors/include/ED_object.h @@ -63,7 +63,6 @@ struct Base *ED_object_add_duplicate(struct Scene *scene, struct Base *base, int #define EM_FREEDATA 1 #define EM_FREEUNDO 2 #define EM_WAITCURSOR 4 -#define EM_DO_UNDO 8 void ED_object_exit_editmode(struct bContext *C, int flag); void ED_object_enter_editmode(struct bContext *C, int flag); diff --git a/source/blender/editors/include/ED_particle.h b/source/blender/editors/include/ED_particle.h index 43cb5053f48..0e5d7302837 100644 --- a/source/blender/editors/include/ED_particle.h +++ b/source/blender/editors/include/ED_particle.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: ED_editparticle.h $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/include/ED_previewrender.h b/source/blender/editors/include/ED_previewrender.h index 10067510e53..c74cb0f9958 100644 --- a/source/blender/editors/include/ED_previewrender.h +++ b/source/blender/editors/include/ED_previewrender.h @@ -29,14 +29,17 @@ struct View3D; struct SpaceButs; struct RenderInfo; -struct Scene; struct Image; +struct ScrArea; +struct uiBlock; struct Render; struct bContext; struct ID; #define PREVIEW_RENDERSIZE 140 +typedef void (*VectorDrawFunc)(int x, int y, int w, int h, float alpha); + /* stores rendered preview - is also used for icons */ typedef struct RenderInfo { int pr_rectx; @@ -71,7 +74,6 @@ void ED_preview_init_dbase(void); void ED_preview_free_dbase(void); void ED_preview_shader_job(const struct bContext *C, void *owner, struct ID *id, int sizex, int sizey); -void ED_preview_iconrender(struct Scene *scene, struct ID *id, int *rect, int sizex, int sizey); void ED_preview_draw(const struct bContext *C, void *idp, rcti *rect); diff --git a/source/blender/editors/include/ED_view3d.h b/source/blender/editors/include/ED_view3d.h index b576299c1d0..38e52a8f59c 100644 --- a/source/blender/editors/include/ED_view3d.h +++ b/source/blender/editors/include/ED_view3d.h @@ -132,8 +132,6 @@ int lasso_inside_edge(short mcords[][2], short moves, int x0, int y0, int x1, in /* modes */ void ED_view3d_exit_paint_modes(struct bContext *C); -/* get 3d region from context, also if mouse is in header or toolbar */ -struct RegionView3D *ED_view3d_context_rv3d(struct bContext *C); #endif /* ED_VIEW3D_H */ diff --git a/source/blender/editors/include/UI_icons.h b/source/blender/editors/include/UI_icons.h index 602e94838b7..a38dfd93c30 100644 --- a/source/blender/editors/include/UI_icons.h +++ b/source/blender/editors/include/UI_icons.h @@ -74,8 +74,8 @@ DEF_ICON(ICON_CHECKBOX_DEHLT) DEF_ICON(ICON_CHECKBOX_HLT) DEF_ICON(ICON_UNLOCKED) DEF_ICON(ICON_LOCKED) -DEF_ICON(ICON_UNPINNED) DEF_ICON(ICON_PINNED) +DEF_ICON(ICON_UNPINNED) DEF_ICON(ICON_BLANK015) DEF_ICON(ICON_RIGHTARROW) DEF_ICON(ICON_DOWNARROW_HLT) @@ -658,12 +658,12 @@ DEF_ICON(ICON_SNAP_VERTEX) DEF_ICON(ICON_SNAP_EDGE) DEF_ICON(ICON_SNAP_FACE) DEF_ICON(ICON_SNAP_VOLUME) -DEF_ICON(ICON_UVS_FACE) DEF_ICON(ICON_STICKY_UVS_LOC) DEF_ICON(ICON_STICKY_UVS_DISABLE) DEF_ICON(ICON_STICKY_UVS_VERT) DEF_ICON(ICON_CLIPUV_DEHLT) DEF_ICON(ICON_CLIPUV_HLT) +DEF_ICON(ICON_BLANK219) DEF_ICON(ICON_SNAP_PEEL_OBJECT) DEF_ICON(ICON_BLANK221) DEF_ICON(ICON_GRID) diff --git a/source/blender/editors/include/UI_interface.h b/source/blender/editors/include/UI_interface.h index 333536137cc..c53087464c0 100644 --- a/source/blender/editors/include/UI_interface.h +++ b/source/blender/editors/include/UI_interface.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: UI_interface.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -53,8 +53,6 @@ struct uiStyle; struct uiFontStyle; struct ColorBand; struct CurveMapping; -struct Image; -struct ImageUser; typedef struct uiBut uiBut; typedef struct uiBlock uiBlock; @@ -417,7 +415,7 @@ void uiBlockPickerButtons(struct uiBlock *block, float *col, float *hsv, float * void uiBlockColorbandButtons(struct uiBlock *block, struct ColorBand *coba, struct rctf *butr, int event); uiBut *uiDefAutoButR(uiBlock *block, struct PointerRNA *ptr, struct PropertyRNA *prop, int index, char *name, int icon, int x1, int y1, int x2, int y2); -void uiDefAutoButsRNA(const struct bContext *C, uiLayout *layout, struct PointerRNA *ptr, int columns); +void uiDefAutoButsRNA(const struct bContext *C, uiLayout *layout, struct PointerRNA *ptr); /* Links * @@ -454,9 +452,9 @@ typedef void (*uiButSearchFunc)(const struct bContext *C, void *arg, char *str, typedef void (*uiBlockHandleFunc)(struct bContext *C, void *arg, int event); /* use inside searchfunc to add items */ -int uiSearchItemAdd(uiSearchItems *items, const char *name, void *poin, int iconid); +int uiSearchItemAdd(uiSearchItems *items, const char *name, void *poin); /* bfunc gets search item *poin as arg2, or if NULL the old string */ -void uiButSetSearchFunc (uiBut *but, uiButSearchFunc sfunc, void *arg1, uiButHandleFunc bfunc, void *active); +void uiButSetSearchFunc (uiBut *but, uiButSearchFunc sfunc, void *arg1, uiButHandleFunc bfunc); /* height in pixels, it's using hardcoded values still */ int uiSearchBoxhHeight(void); @@ -609,15 +607,13 @@ uiBlock *uiLayoutFreeBlock(uiLayout *layout); /* templates */ void uiTemplateHeader(uiLayout *layout, struct bContext *C); void uiTemplateID(uiLayout *layout, struct bContext *C, struct PointerRNA *ptr, char *propname, - char *newop, char *unlinkop); + char *newop, char *openop, char *unlinkop); uiLayout *uiTemplateModifier(uiLayout *layout, struct PointerRNA *ptr); uiLayout *uiTemplateConstraint(uiLayout *layout, struct PointerRNA *ptr); void uiTemplatePreview(uiLayout *layout, struct ID *id); void uiTemplateColorRamp(uiLayout *layout, struct ColorBand *coba, int expand); void uiTemplateCurveMapping(uiLayout *layout, struct CurveMapping *cumap, int type); void uiTemplateLayers(uiLayout *layout, struct PointerRNA *ptr, char *propname); -void uiTemplateImageLayers(uiLayout *layout, struct bContext *C, struct Image *ima, struct ImageUser *iuser); -ListBase uiTemplateList(uiLayout *layout, struct PointerRNA *ptr, char *propname, char *activeprop, int rows, int columns, int compact); /* items */ void uiItemO(uiLayout *layout, char *name, int icon, char *opname); @@ -634,7 +630,6 @@ void uiItemR(uiLayout *layout, char *name, int icon, struct PointerRNA *ptr, cha void uiItemFullR(uiLayout *layout, char *name, int icon, struct PointerRNA *ptr, struct PropertyRNA *prop, int index, int value, int expand, int slider, int toggle); void uiItemEnumR(uiLayout *layout, char *name, int icon, struct PointerRNA *ptr, char *propname, int value); void uiItemsEnumR(uiLayout *layout, struct PointerRNA *ptr, char *propname); -void uiItemPointerR(uiLayout *layout, char *name, int icon, struct PointerRNA *ptr, char *propname, struct PointerRNA *searchptr, char *searchpropname); void uiItemL(uiLayout *layout, char *name, int icon); /* label */ void uiItemM(uiLayout *layout, struct bContext *C, char *name, int icon, char *menuname); /* menu */ diff --git a/source/blender/editors/include/UI_resources.h b/source/blender/editors/include/UI_resources.h index 1ae3634c73b..7168e593a8a 100644 --- a/source/blender/editors/include/UI_resources.h +++ b/source/blender/editors/include/UI_resources.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: UI_resources.h 13057 2007-12-30 12:08:28Z aligorith $ * * ***** BEGIN GPL/BL DUAL LICENSE BLOCK ***** * diff --git a/source/blender/editors/interface/Makefile b/source/blender/editors/interface/Makefile index a3d0692f1e1..dfc8187de49 100644 --- a/source/blender/editors/interface/Makefile +++ b/source/blender/editors/interface/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/interface/interface.c b/source/blender/editors/interface/interface.c index fcea74cc22b..5ffc6440dc4 100644 --- a/source/blender/editors/interface/interface.c +++ b/source/blender/editors/interface/interface.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: interface.c 16882 2008-10-02 12:29:45Z ton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -80,6 +80,7 @@ */ static void ui_free_but(const bContext *C, uiBut *but); +static void ui_rna_ID_autocomplete(bContext *C, char *str, void *arg_but); /* ************* translation ************** */ @@ -670,8 +671,7 @@ void uiDrawBlock(const bContext *C, uiBlock *block) /* widgets */ for(but= block->buttons.first; but; but= but->next) { ui_but_to_pixelrect(&rect, ar, block, but); - if(!(but->flag & UI_HIDDEN)) - ui_draw_but(C, ar, &style, but, &rect); + ui_draw_but(C, ar, &style, but, &rect); } /* restore matrix */ @@ -1281,13 +1281,17 @@ void ui_get_but_string(uiBut *but, char *str, int maxlen) else if(type == PROP_POINTER) { /* RNA pointer */ PointerRNA ptr= RNA_property_pointer_get(&but->rnapoin, but->rnaprop); - buf= RNA_struct_name_get_alloc(&ptr, str, maxlen); - } + PropertyRNA *nameprop; - if(!buf) { - BLI_strncpy(str, "", maxlen); + if(ptr.data && (nameprop = RNA_struct_name_property(ptr.type))) + buf= RNA_property_string_get_alloc(&ptr, nameprop, str, maxlen); + else + BLI_strncpy(str, "", maxlen); } - else if(buf && buf != str) { + else + BLI_strncpy(str, "", maxlen); + + if(buf && buf != str) { /* string was too long, we have to truncate */ BLI_strncpy(str, buf, maxlen); MEM_freeN(buf); @@ -1333,6 +1337,72 @@ void ui_get_but_string(uiBut *but, char *str, int maxlen) } } +static void ui_rna_ID_collection(bContext *C, uiBut *but, PointerRNA *ptr, PropertyRNA **prop) +{ + CollectionPropertyIterator iter; + PropertyRNA *iterprop, *iprop; + StructRNA *srna; + + /* look for collection property in Main */ + RNA_pointer_create(NULL, &RNA_Main, CTX_data_main(C), ptr); + + iterprop= RNA_struct_iterator_property(ptr->type); + RNA_property_collection_begin(ptr, iterprop, &iter); + *prop= NULL; + + for(; iter.valid; RNA_property_collection_next(&iter)) { + iprop= iter.ptr.data; + + /* if it's a collection and has same pointer type, we've got it */ + if(RNA_property_type(iprop) == PROP_COLLECTION) { + srna= RNA_property_pointer_type(ptr, iprop); + + if(RNA_property_pointer_type(ptr, but->rnaprop) == srna) { + *prop= iprop; + break; + } + } + } + + RNA_property_collection_end(&iter); +} + +/* autocomplete callback for RNA pointers */ +static void ui_rna_ID_autocomplete(bContext *C, char *str, void *arg_but) +{ + uiBut *but= arg_but; + AutoComplete *autocpl; + CollectionPropertyIterator iter; + PointerRNA ptr; + PropertyRNA *prop, *nameprop; + char *name; + + if(str[0]==0) return; + + /* get the collection */ + ui_rna_ID_collection(C, but, &ptr, &prop); + if(prop==NULL) return; + + autocpl= autocomplete_begin(str, ui_get_but_string_max_length(but)); + RNA_property_collection_begin(&ptr, prop, &iter); + + /* loop over items in collection */ + for(; iter.valid; RNA_property_collection_next(&iter)) { + if(iter.ptr.data && (nameprop = RNA_struct_name_property(iter.ptr.type))) { + name= RNA_property_string_get_alloc(&iter.ptr, nameprop, NULL, 0); + + if(name) { + /* test item name */ + autocomplete_do_name(autocpl, name); + MEM_freeN(name); + } + } + } + + RNA_property_collection_end(&iter); + autocomplete_end(autocpl, str); +} + int ui_set_but_string(bContext *C, uiBut *but, const char *str) { if(but->rnaprop && ELEM3(but->type, TEX, IDPOIN, SEARCH_MENU)) { @@ -1351,21 +1421,21 @@ int ui_set_but_string(bContext *C, uiBut *but, const char *str) PointerRNA ptr, rptr; PropertyRNA *prop; + /* XXX only ID pointers at the moment, needs to support + * custom collection too for bones, vertex groups, .. */ + ui_rna_ID_collection(C, but, &ptr, &prop); + if(str == NULL || str[0] == '\0') { - RNA_property_pointer_set(&but->rnapoin, but->rnaprop, PointerRNA_NULL); + memset(&rptr, 0, sizeof(rptr)); + RNA_property_pointer_set(&but->rnapoin, but->rnaprop, rptr); return 1; } - else { - ptr= but->rnasearchpoin; - prop= but->rnasearchprop; - - if(prop && RNA_property_collection_lookup_string(&ptr, prop, str, &rptr)) - RNA_property_pointer_set(&but->rnapoin, but->rnaprop, rptr); - + else if(prop && RNA_property_collection_lookup_string(&ptr, prop, str, &rptr)) { + RNA_property_pointer_set(&but->rnapoin, but->rnaprop, rptr); return 1; } - - return 0; + else + return 0; } } } @@ -2077,10 +2147,13 @@ static uiBut *ui_def_but(uiBlock *block, int type, int retval, char *str, short rgb_to_hsv(rgb[0], rgb[1], rgb[2], but->hsv, but->hsv+1, but->hsv+2); } - if((block->flag & UI_BLOCK_LOOP) || ELEM7(but->type, MENU, TEX, LABEL, IDPOIN, BLOCK, BUTM, SEARCH_MENU)) - but->flag |= (UI_TEXT_LEFT|UI_ICON_LEFT); - else if(but->type==BUT_TOGDUAL) + if((block->flag & UI_BLOCK_LOOP) || ELEM6(but->type, MENU, TEX, LABEL, IDPOIN, BLOCK, BUTM)) { + but->flag |= UI_TEXT_LEFT; + } + + if(but->type==BUT_TOGDUAL) { but->flag |= UI_ICON_LEFT; + } but->flag |= (block->flag & UI_BUT_ALIGN); @@ -2230,6 +2303,10 @@ uiBut *ui_def_but_rna(uiBlock *block, int type, int retval, char *str, short x1, but->rnaindex= index; else but->rnaindex= 0; + + if(type == IDPOIN) + uiButSetCompleteFunc(but, ui_rna_ID_autocomplete, but); + } if(icon) { @@ -2345,11 +2422,7 @@ void autocomplete_do_name(AutoComplete *autocpl, const char *name) else { /* remove from truncate what is not in bone->name */ for(a=0; a<autocpl->maxlen-1; a++) { - if(name[a] == 0) { - truncate[a]= 0; - break; - } - else if(truncate[a]!=name[a]) + if(truncate[a]!=name[a]) truncate[a]= 0; } } @@ -2680,7 +2753,7 @@ void uiBlockFlipOrder(uiBlock *block) uiBut *but, *next; float centy, miny=10000, maxy= -10000; - if(U.uiflag & USER_MENUFIXEDORDER) + if(!(U.uiflag & USER_DIRECTIONALORDER)) return; for(but= block->buttons.first; but; but= but->next) { @@ -2919,15 +2992,15 @@ uiBut *uiDefSearchBut(uiBlock *block, void *arg, int retval, int icon, int maxle } /* arg is user value, searchfunc and handlefunc both get it as arg */ -/* if active set, button opens with this item visible and selected */ -void uiButSetSearchFunc(uiBut *but, uiButSearchFunc sfunc, void *arg, uiButHandleFunc bfunc, void *active) +void uiButSetSearchFunc(uiBut *but, uiButSearchFunc sfunc, void *arg, uiButHandleFunc bfunc) { but->search_func= sfunc; but->search_arg= arg; - uiButSetFunc(but, bfunc, arg, active); + uiButSetFunc(but, bfunc, arg, NULL); } + /* Program Init/Exit */ void UI_init(void) diff --git a/source/blender/editors/interface/interface_draw.c b/source/blender/editors/interface/interface_draw.c index 8400fee0c55..6d6d4ab9299 100644 --- a/source/blender/editors/interface/interface_draw.c +++ b/source/blender/editors/interface/interface_draw.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: interface_draw.c 15733 2008-07-24 09:23:13Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/interface/interface_handlers.c b/source/blender/editors/interface/interface_handlers.c index 92c888ac772..fb5afbf5e36 100644 --- a/source/blender/editors/interface/interface_handlers.c +++ b/source/blender/editors/interface/interface_handlers.c @@ -112,9 +112,6 @@ typedef struct uiHandleButtonData { /* tooltip */ ARegion *tooltip; wmTimer *tooltiptimer; - - /* auto open */ - int used_mouse; wmTimer *autoopentimer; /* text selection/editing */ @@ -407,15 +404,7 @@ static void ui_apply_but_TOG(bContext *C, uiBlock *block, uiBut *but, uiHandleBu static void ui_apply_but_ROW(bContext *C, uiBlock *block, uiBut *but, uiHandleButtonData *data) { - uiBut *bt; - ui_set_but_val(but, but->hardmax); - - /* states of other row buttons */ - for(bt= block->buttons.first; bt; bt= bt->next) - if(bt!=but && bt->poin==but->poin && bt->type==ROW) - ui_check_but(bt); - ui_apply_but_func(C, but); data->retval= but->retval; @@ -749,8 +738,11 @@ static void ui_apply_button(bContext *C, uiBlock *block, uiBut *but, uiHandleBut ui_apply_but_ROW(C, block, but, data); break; case SCROLL: + break; case NUM: case NUMABS: + ui_apply_but_NUM(C, but, data); + break; case SLI: case NUMSLI: ui_apply_but_NUM(C, but, data); @@ -1226,14 +1218,8 @@ static int ui_textedit_autocomplete(bContext *C, uiBut *but, uiHandleButtonData int changed= 1; str= data->str; - - if(data->searchbox) - ui_searchbox_autocomplete(C, data->searchbox, but, data->str); - else - but->autocomplete_func(C, str, but->autofunc_arg); - + but->autocomplete_func(C, str, but->autofunc_arg); but->pos= strlen(str); - but->selsta= but->selend= but->pos; return changed; } @@ -1360,14 +1346,14 @@ static void ui_textedit_next_but(uiBlock *block, uiBut *actbut, uiHandleButtonDa return; for(but= actbut->next; but; but= but->next) { - if(ELEM7(but->type, TEX, NUM, NUMABS, NUMSLI, HSVSLI, IDPOIN, SEARCH_MENU)) { + if(ELEM5(but->type, TEX, NUM, NUMABS, NUMSLI, HSVSLI)) { data->postbut= but; data->posttype= BUTTON_ACTIVATE_TEXT_EDITING; return; } } for(but= block->buttons.first; but!=actbut; but= but->next) { - if(ELEM7(but->type, TEX, NUM, NUMABS, NUMSLI, HSVSLI, IDPOIN, SEARCH_MENU)) { + if(ELEM5(but->type, TEX, NUM, NUMABS, NUMSLI, HSVSLI)) { data->postbut= but; data->posttype= BUTTON_ACTIVATE_TEXT_EDITING; return; @@ -1384,14 +1370,14 @@ static void ui_textedit_prev_but(uiBlock *block, uiBut *actbut, uiHandleButtonDa return; for(but= actbut->prev; but; but= but->prev) { - if(ELEM7(but->type, TEX, NUM, NUMABS, NUMSLI, HSVSLI, IDPOIN, SEARCH_MENU)) { + if(ELEM5(but->type, TEX, NUM, NUMABS, NUMSLI, HSVSLI)) { data->postbut= but; data->posttype= BUTTON_ACTIVATE_TEXT_EDITING; return; } } for(but= block->buttons.last; but!=actbut; but= but->prev) { - if(ELEM7(but->type, TEX, NUM, NUMABS, NUMSLI, HSVSLI, IDPOIN, SEARCH_MENU)) { + if(ELEM5(but->type, TEX, NUM, NUMABS, NUMSLI, HSVSLI)) { data->postbut= but; data->posttype= BUTTON_ACTIVATE_TEXT_EDITING; return; @@ -1447,6 +1433,7 @@ static void ui_do_but_textedit(bContext *C, uiBlock *block, uiBut *but, uiHandle } } else if(inbox) { + printf("release inside \n"); button_activate_state(C, but, BUTTON_STATE_EXIT); retval= WM_UI_HANDLER_BREAK; } @@ -1515,7 +1502,7 @@ static void ui_do_but_textedit(bContext *C, uiBlock *block, uiBut *but, uiHandle case TABKEY: /* there is a key conflict here, we can't tab with autocomplete */ - if(but->autocomplete_func || data->searchbox) { + if(but->autocomplete_func) { changed= ui_textedit_autocomplete(C, but, data); retval= WM_UI_HANDLER_BREAK; } @@ -2066,11 +2053,6 @@ static int ui_numedit_but_SLI(uiBut *but, uiHandleButtonData *data, int shift, i if(but->type==NUMSLI) deler= ((but->x2-but->x1) - 5.0*but->aspect); else if(but->type==HSVSLI) deler= ((but->x2-but->x1)/2 - 5.0*but->aspect); - else if(but->type==SCROLL) { - int horizontal= (but->x2 - but->x1 > but->y2 - but->y1); - float size= (horizontal)? (but->x2-but->x1): -(but->y2-but->y1); - deler= size*(but->softmax - but->softmin)/(but->softmax - but->softmin + but->a1); - } else deler= (but->x2-but->x1- 5.0*but->aspect); f= (float)(mx-data->dragstartx)/deler + data->dragfstart; @@ -2241,54 +2223,6 @@ static int ui_do_but_SLI(bContext *C, uiBlock *block, uiBut *but, uiHandleButton return retval; } -static int ui_do_but_SCROLL(bContext *C, uiBlock *block, uiBut *but, uiHandleButtonData *data, wmEvent *event) -{ - int mx, my, click= 0; - int retval= WM_UI_HANDLER_CONTINUE; - int horizontal= (but->x2 - but->x1 > but->y2 - but->y1); - - mx= event->x; - my= event->y; - ui_window_to_block(data->region, block, &mx, &my); - - if(data->state == BUTTON_STATE_HIGHLIGHT) { - if(event->val==KM_PRESS) { - if(event->type == LEFTMOUSE) { - if(horizontal) { - data->dragstartx= mx; - data->draglastx= mx; - } - else { - data->dragstartx= my; - data->draglastx= my; - } - button_activate_state(C, but, BUTTON_STATE_NUM_EDITING); - retval= WM_UI_HANDLER_BREAK; - } - else if(ELEM(event->type, PADENTER, RETKEY) && event->val==KM_PRESS) - click= 1; - } - } - else if(data->state == BUTTON_STATE_NUM_EDITING) { - if(event->type == ESCKEY) { - data->cancel= 1; - data->escapecancel= 1; - button_activate_state(C, but, BUTTON_STATE_EXIT); - } - else if(event->type == LEFTMOUSE && event->val!=KM_PRESS) { - button_activate_state(C, but, BUTTON_STATE_EXIT); - } - else if(event->type == MOUSEMOVE) { - if(ui_numedit_but_SLI(but, data, 0, 0, (horizontal)? mx: my)) - ui_numedit_apply(C, block, but, data); - } - - retval= WM_UI_HANDLER_BREAK; - } - - return retval; -} - static int ui_do_but_BLOCK(bContext *C, uiBut *but, uiHandleButtonData *data, wmEvent *event) { @@ -3131,9 +3065,13 @@ static int ui_do_button(bContext *C, uiBlock *block, uiBut *but, wmEvent *event) case OPTIONN: retval= ui_do_but_TOG(C, but, data, event); break; +#if 0 case SCROLL: - retval= ui_do_but_SCROLL(C, block, but, data, event); + /* DrawBut(b, 1); */ + /* do_scrollbut(b); */ + /* DrawBut(b,0); */ break; +#endif case NUM: case NUMABS: retval= ui_do_but_NUM(C, block, but, data, event); @@ -3294,8 +3232,7 @@ static uiBut *ui_but_find_mouse_over(ARegion *ar, int x, int y) for(but=block->buttons.first; but; but= but->next) { if(ELEM3(but->type, LABEL, ROUNDBOX, SEPR)) continue; - if(but->flag & UI_HIDDEN) - continue; + if(ui_but_contains_pt(but, mx, my)) /* give precedence to already activated buttons */ if(!butover || (!butover->active && but->active)) @@ -3347,7 +3284,7 @@ static void button_activate_state(bContext *C, uiBut *but, uiHandleButtonState s /* automatic open pulldown block timer */ if(ELEM3(but->type, BLOCK, PULLDOWN, ICONTEXTROW)) { - if(data->used_mouse && !data->autoopentimer) { + if(!data->autoopentimer) { int time; if(but->block->auto_open==2) time= 1; // test for toolbox @@ -3450,9 +3387,6 @@ static void button_activate_init(bContext *C, ARegion *ar, uiBut *but, uiButtonA if(but->block->auto_open_last+BUTTON_AUTO_OPEN_THRESH < PIL_check_seconds_timer()) but->block->auto_open= 0; - if(type == BUTTON_ACTIVATE_OVER) { - data->used_mouse= 1; - } button_activate_state(C, but, BUTTON_STATE_HIGHLIGHT); if(type == BUTTON_ACTIVATE_OPEN) { @@ -3771,19 +3705,12 @@ static void ui_handle_button_return_submenu(bContext *C, wmEvent *event, uiBut * button_activate_exit(C, data, but, 1); } else if(menu->menuretval == UI_RETURN_OUT) { - if(event->type==MOUSEMOVE && ui_mouse_inside_button(data->region, but, event->x, event->y)) { + if(ui_mouse_inside_button(data->region, but, event->x, event->y)) { button_activate_state(C, but, BUTTON_STATE_HIGHLIGHT); } else { - but= ui_but_find_activated(data->region); - if(but) { - but->active->used_mouse= 0; - button_activate_state(C, but, BUTTON_STATE_HIGHLIGHT); - } - else { - data->cancel= 1; - button_activate_exit(C, data, but, 1); - } + data->cancel= 1; + button_activate_exit(C, data, but, 1); } } } @@ -4122,7 +4049,7 @@ static int ui_handle_menu_return_submenu(bContext *C, wmEvent *event, uiPopupBlo uiBlock *block; uiHandleButtonData *data; uiPopupBlockHandle *submenu; - int mx, my, update; + int mx, my; ar= menu->region; block= ar->uiblocks.first; @@ -4140,16 +4067,14 @@ static int ui_handle_menu_return_submenu(bContext *C, wmEvent *event, uiPopupBlo menu->butretval= data->retval; } } - - update= (submenu->menuretval == UI_RETURN_UPDATE); - if(update) + else if(submenu->menuretval == UI_RETURN_UPDATE) menu->menuretval = UI_RETURN_UPDATE; /* now let activated button in this menu exit, which * will actually close the submenu too */ ui_handle_button_return_submenu(C, event, but); - if(update) + if(submenu->menuretval == UI_RETURN_UPDATE) submenu->menuretval = 0; } diff --git a/source/blender/editors/interface/interface_icons.c b/source/blender/editors/interface/interface_icons.c index 315b8693905..df069069a33 100644 --- a/source/blender/editors/interface/interface_icons.c +++ b/source/blender/editors/interface/interface_icons.c @@ -41,30 +41,28 @@ #include "BLI_blenlib.h" #include "BLI_storage_types.h" -#include "DNA_material_types.h" #include "DNA_screen_types.h" -#include "DNA_scene_types.h" #include "DNA_userdef_types.h" + +#include "BKE_utildefines.h" #include "BKE_image.h" #include "BKE_icons.h" -#include "BKE_utildefines.h" #include "IMB_imbuf.h" #include "IMB_imbuf_types.h" #include "BIF_gl.h" #include "BIF_glutil.h" - -#include "ED_datafiles.h" -#include "ED_previewrender.h" - #include "UI_interface.h" #include "UI_interface_icons.h" -#include "UI_resources.h" /* elubie: should be removed once the enum for the ICONS is in BIF_preview_icons.h */ -#include "interface_intern.h" +// XXX #include "BIF_previewrender.h" +// XXX #include "BIF_screen.h" +#include "UI_resources.h" /* elubie: should be removed once the enum for the ICONS is in BIF_preview_icons.h */ +#include "interface_intern.h" +#include "ED_datafiles.h" #define ICON_IMAGE_W 600 #define ICON_IMAGE_H 640 @@ -652,6 +650,7 @@ void UI_icons_init(int first_dyn_id) init_internal_icons(); } +#if 0 static void icon_copy_rect(ImBuf *ibuf, unsigned int w, unsigned int h, unsigned int *rect) { struct ImBuf *ima; @@ -728,28 +727,21 @@ static void icon_create_mipmap(struct PreviewImage* prv_img, int miplevel) } /* create single icon from jpg, png etc. */ -static void icon_from_image(Scene *scene, Image *img, int miplevel) +static void icon_from_image(Image *img, int miplevel) { - ImBuf *ibuf= NULL; - ImageUser iuser; - PreviewImage *pi; unsigned int pr_size; short image_loaded = 0; + struct ImBuf* ibuf=NULL; + PreviewImage* pi; /* img->ok is zero when Image cannot load */ if (img==NULL || img->ok==0) return; - /* setup dummy image user */ - memset(&iuser, 0, sizeof(ImageUser)); - iuser.ok= iuser.framenr= 1; - iuser.scene= scene; - /* elubie: this needs to be changed: here image is always loaded if not already there. Very expensive for large images. Need to find a way to only get existing ibuf */ - - ibuf = BKE_image_get_ibuf(img, &iuser); + ibuf = BKE_image_get_ibuf(img, NULL); if(ibuf==NULL || ibuf->rect==NULL) { return; } @@ -779,14 +771,18 @@ static void set_alpha(char* cp, int sizex, int sizey, char alpha) } } } +#endif /* only called when icon has changed */ /* only call with valid pointer from UI_icon_draw */ -static void icon_set_image(Scene *scene, ID *id, PreviewImage* prv_img, int miplevel) +static void icon_set_image(ID *id, DrawInfo *di, PreviewImage* prv_img, int miplevel) { +#if 0 // XXX - preview renders have to be redesigned - possibly low level op (elubie) RenderInfo ri; unsigned int pr_size = 0; + if (!di) return; + if (!prv_img) { printf("No preview image for this ID: %s\n", id->name); return; @@ -795,19 +791,20 @@ static void icon_set_image(Scene *scene, ID *id, PreviewImage* prv_img, int mipl /* no drawing (see last parameter doDraw, just calculate preview image - hopefully small enough to be fast */ if (GS(id->name) == ID_IM) - icon_from_image(scene, (struct Image*)id, miplevel); + icon_from_image((struct Image*)id, miplevel); else { /* create the preview rect */ icon_create_mipmap(prv_img, miplevel); ri.curtile= 0; ri.tottile= 0; + ri.rect = NULL; ri.pr_rectx = prv_img->w[miplevel]; ri.pr_recty = prv_img->h[miplevel]; + pr_size = ri.pr_rectx*ri.pr_recty*sizeof(unsigned int); - ri.rect = MEM_callocN(pr_size, "pr icon rect"); - ED_preview_iconrender(scene, id, ri.rect, ri.pr_rectx, ri.pr_recty); + BIF_previewrender(id, &ri, NULL, PR_ICON_RENDER); /* world is rendered with alpha=0, so it wasn't displayed this could be render option for sky to, for later */ @@ -821,11 +818,15 @@ static void icon_set_image(Scene *scene, ID *id, PreviewImage* prv_img, int mipl } } - memcpy(prv_img->rect[miplevel], ri.rect, pr_size); + if (ri.rect) { + memcpy(prv_img->rect[miplevel], ri.rect, pr_size); - /* and clean up */ - MEM_freeN(ri.rect); + /* and clean up */ + MEM_freeN(ri.rect); + ri.rect = 0; + } } +#endif } static void icon_draw_rect(float x, float y, int w, int h, float aspect, int rw, int rh, unsigned int *rect) @@ -911,7 +912,14 @@ static void icon_draw_size(float x, float y, int icon_id, float aspect, int mipl PreviewImage* pi = BKE_previewimg_get((ID*)icon->obj); if (pi) { - /* no create icon on this level in code */ + if (!nocreate && (pi->changed[miplevel] ||!pi->rect[miplevel])) /* changed only ever set by dynamic icons */ + { + // XXX waitcursor(1); + /* create the preview rect if necessary */ + icon_set_image((ID*)icon->obj, icon->drawinfo, pi, miplevel); + pi->changed[miplevel] = 0; + // XXX waitcursor(0); + } if (!pi->rect[miplevel]) return; /* something has gone wrong! */ @@ -920,43 +928,6 @@ static void icon_draw_size(float x, float y, int icon_id, float aspect, int mipl } } -void ui_id_icon_render(Scene *scene, ID *id) -{ - PreviewImage *pi = BKE_previewimg_get(id); - - if (pi) { - if ((pi->changed[0] ||!pi->rect[0])) /* changed only ever set by dynamic icons */ - { - /* create the preview rect if necessary */ - icon_set_image(scene, id, pi, 0); - pi->changed[0] = 0; - } - } -} - -int ui_id_icon_get(Scene *scene, ID *id) -{ - int iconid= 0; - - /* icon */ - switch(GS(id->name)) - { - case ID_MA: /* fall through */ - case ID_TE: /* fall through */ - case ID_IM: /* fall through */ - case ID_WO: /* fall through */ - case ID_LA: /* fall through */ - iconid= BKE_icon_getid(id); - /* checks if not exists, or changed */ - ui_id_icon_render(scene, id); - break; - default: - break; - } - - return iconid; -} - static void icon_draw_mipmap(float x, float y, int icon_id, float aspect, int miplevel, int nocreate) { int draw_size = preview_size(miplevel); diff --git a/source/blender/editors/interface/interface_intern.h b/source/blender/editors/interface/interface_intern.h index 1b16155c7e6..3aed2a7c299 100644 --- a/source/blender/editors/interface/interface_intern.h +++ b/source/blender/editors/interface/interface_intern.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: interface.h 14444 2008-04-16 22:40:48Z hos $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -44,17 +44,12 @@ struct uiStyle; struct uiWidgetColors; struct uiLayout; struct bContextStore; -struct Scene; -struct ID; /* ****************** general defines ************** */ /* visual types for drawing */ /* for time being separated from functional types */ typedef enum { - /* default */ - UI_WTYPE_REGULAR, - /* standard set */ UI_WTYPE_LABEL, UI_WTYPE_TOGGLE, @@ -83,8 +78,7 @@ typedef enum { UI_WTYPE_SWATCH, UI_WTYPE_RGB_PICKER, UI_WTYPE_NORMAL, - UI_WTYPE_BOX, - UI_WTYPE_SCROLL + UI_WTYPE_BOX } uiWidgetTypeEnum; @@ -104,7 +98,7 @@ typedef enum { #define UI_ACTIVE 4 #define UI_HAS_ICON 8 #define UI_TEXTINPUT 16 -#define UI_HIDDEN 32 + /* warn: rest of uiBut->flag in UI_interface.h */ /* internal panel drawing defines */ @@ -211,9 +205,6 @@ struct uiBut { struct PropertyRNA *rnaprop; int rnaindex; - struct PointerRNA rnasearchpoin; - struct PropertyRNA *rnasearchprop; - /* Operator data */ struct wmOperatorType *optype; int opcontext; @@ -374,7 +365,6 @@ void ui_tooltip_free(struct bContext *C, struct ARegion *ar); ARegion *ui_searchbox_create(struct bContext *C, struct ARegion *butregion, uiBut *but); int ui_searchbox_inside(struct ARegion *ar, int x, int y); void ui_searchbox_update(struct bContext *C, struct ARegion *ar, uiBut *but, int reset); -void ui_searchbox_autocomplete(struct bContext *C, struct ARegion *ar, uiBut *but, char *str); void ui_searchbox_event(struct bContext *C, struct ARegion *ar, uiBut *but, struct wmEvent *event); void ui_searchbox_apply(uiBut *but, struct ARegion *ar); void ui_searchbox_free(struct bContext *C, struct ARegion *ar); @@ -426,15 +416,11 @@ extern void ui_draw_but(const struct bContext *C, ARegion *ar, struct uiStyle *s struct ThemeUI; void ui_widget_color_init(struct ThemeUI *tui); -void ui_draw_menu_item(struct uiFontStyle *fstyle, rcti *rect, char *name, int iconid, int state); +void ui_draw_menu_item(struct uiFontStyle *fstyle, rcti *rect, char *name, int state); /* interface_style.c */ void uiStyleInit(void); -/* interface_icons.c */ -void ui_id_icon_render(struct Scene *scene, struct ID *id); -int ui_id_icon_get(struct Scene *scene, struct ID *id); - /* resources.c */ void init_userdef_do_versions(void); void ui_theme_init_userdef(void); @@ -442,9 +428,8 @@ void ui_resources_init(void); void ui_resources_free(void); /* interface_layout.c */ -void ui_layout_add_but(uiLayout *layout, uiBut *but); +void ui_layout_add_but(struct uiLayout *layout, uiBut *but); int ui_but_can_align(uiBut *but); -void ui_but_add_search(uiBut *but, PointerRNA *ptr, PropertyRNA *prop, PointerRNA *searchptr, PropertyRNA *searchprop); /* interface_anim.c */ void ui_but_anim_flag(uiBut *but, float cfra); diff --git a/source/blender/editors/interface/interface_layout.c b/source/blender/editors/interface/interface_layout.c index f9816235b88..9101fd743ee 100644 --- a/source/blender/editors/interface/interface_layout.c +++ b/source/blender/editors/interface/interface_layout.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: interface_layout.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -455,10 +455,9 @@ static void ui_item_enum_row(uiLayout *layout, uiBlock *block, PointerRNA *ptr, } /* create label + button for RNA property */ -static uiBut *ui_item_with_label(uiLayout *layout, uiBlock *block, char *name, int icon, PointerRNA *ptr, PropertyRNA *prop, int index, int x, int y, int w, int h) +static void ui_item_with_label(uiLayout *layout, uiBlock *block, char *name, int icon, PointerRNA *ptr, PropertyRNA *prop, int index, int x, int y, int w, int h) { uiLayout *sub; - uiBut *but; PropertySubType subtype; sub= uiLayoutRow(layout, 0); @@ -474,13 +473,12 @@ static uiBut *ui_item_with_label(uiLayout *layout, uiBlock *block, char *name, i if(subtype == PROP_FILEPATH || subtype == PROP_DIRPATH) { uiBlockSetCurLayout(block, uiLayoutRow(sub, 1)); uiDefAutoButR(block, ptr, prop, index, "", icon, x, y, w-UI_UNIT_X, h); - but= uiDefIconBut(block, BUT, 0, ICON_FILESEL, x, y, UI_UNIT_X, h, NULL, 0.0f, 0.0f, 0.0f, 0.0f, "DUMMY file select button"); /* XXX */ + uiDefIconBut(block, BUT, 0, ICON_FILESEL, x, y, UI_UNIT_X, h, NULL, 0.0f, 0.0f, 0.0f, 0.0f, "DUMMY file select button"); /* XXX */ } else - but= uiDefAutoButR(block, ptr, prop, index, "", icon, x, y, w, h); + uiDefAutoButR(block, ptr, prop, index, "", icon, x, y, w, h); uiBlockSetCurLayout(block, layout); - return but; } /********************* Button Items *************************/ @@ -603,7 +601,7 @@ void uiItemsEnumO(uiLayout *layout, char *opname, char *propname) RNA_property_enum_items(&ptr, prop, &item, &totitem); for(i=0; i<totitem; i++) - uiItemEnumO(layout, (char*)item[i].name, item[i].icon, opname, propname, item[i].value); + uiItemEnumO(layout, NULL, 0, opname, propname, item[i].value); } } @@ -718,8 +716,6 @@ static void ui_item_rna_size(uiLayout *layout, char *name, int icon, PropertyRNA else if(ui_layout_vary_direction(layout) == UI_ITEM_VARY_X) { if(type == PROP_BOOLEAN && strcmp(name, "") != 0) w += UI_UNIT_X; - else if(type == PROP_ENUM) - w += UI_UNIT_X/2; } *r_w= w; @@ -749,11 +745,9 @@ void uiItemFullR(uiLayout *layout, char *name, int icon, PointerRNA *ptr, Proper if(!icon) icon= RNA_property_ui_icon(prop); - if(ELEM4(type, PROP_INT, PROP_FLOAT, PROP_STRING, PROP_POINTER)) - name= ui_item_name_add_colon(name, namestr); - else if(type == PROP_BOOLEAN && len) + if(ELEM5(type, PROP_INT, PROP_FLOAT, PROP_STRING, PROP_ENUM, PROP_POINTER)) name= ui_item_name_add_colon(name, namestr); - else if(type == PROP_ENUM && index != RNA_ENUM_VALUE) + if(type == PROP_BOOLEAN && len) name= ui_item_name_add_colon(name, namestr); if(layout->root->type == UI_LAYOUT_MENU) { @@ -784,10 +778,8 @@ void uiItemFullR(uiLayout *layout, char *name, int icon, PointerRNA *ptr, Proper else if(type == PROP_ENUM && expand) ui_item_enum_row(layout, block, ptr, prop, name, 0, 0, w, h); /* property with separate label */ - else if(type == PROP_ENUM || type == PROP_STRING || type == PROP_POINTER) { - but= ui_item_with_label(layout, block, name, icon, ptr, prop, index, 0, 0, w, h); - ui_but_add_search(but, ptr, prop, NULL, NULL); - } + else if(type == PROP_ENUM || type == PROP_STRING || type == PROP_POINTER) + ui_item_with_label(layout, block, name, icon, ptr, prop, index, 0, 0, w, h); /* single button */ else { but= uiDefAutoButR(block, ptr, prop, index, (char*)name, icon, 0, 0, w, h); @@ -858,142 +850,6 @@ void uiItemsEnumR(uiLayout *layout, struct PointerRNA *ptr, char *propname) } } -/* Pointer RNA button with search */ - -static void rna_search_cb(const struct bContext *C, void *arg_but, char *str, uiSearchItems *items) -{ - Scene *scene= CTX_data_scene(C); - uiBut *but= arg_but; - char *name; - int i, iconid; - - i = 0; - RNA_PROP_BEGIN(&but->rnasearchpoin, itemptr, but->rnasearchprop) { - iconid= 0; - if(RNA_struct_is_ID(itemptr.type)) - iconid= ui_id_icon_get(scene, itemptr.data); - - name= RNA_struct_name_get_alloc(&itemptr, NULL, 0); - - if(name) { - if(BLI_strcasestr(name, str)) { - if(!uiSearchItemAdd(items, name, SET_INT_IN_POINTER(i), iconid)) { - MEM_freeN(name); - break; - } - } - - MEM_freeN(name); - } - - i++; - } - RNA_PROP_END; -} - -static void search_id_collection(StructRNA *ptype, PointerRNA *ptr, PropertyRNA **prop) -{ - StructRNA *srna; - - /* look for collection property in Main */ - RNA_main_pointer_create(G.main, ptr); - - *prop= NULL; - - RNA_STRUCT_BEGIN(ptr, iprop) { - /* if it's a collection and has same pointer type, we've got it */ - if(RNA_property_type(iprop) == PROP_COLLECTION) { - srna= RNA_property_pointer_type(ptr, iprop); - - if(ptype == srna) { - *prop= iprop; - break; - } - } - } - RNA_STRUCT_END; -} - -void ui_but_add_search(uiBut *but, PointerRNA *ptr, PropertyRNA *prop, PointerRNA *searchptr, PropertyRNA *searchprop) -{ - StructRNA *ptype; - PointerRNA sptr; - - /* for ID's we do automatic lookup */ - if(!searchprop) { - if(RNA_property_type(prop) == PROP_POINTER) { - ptype= RNA_property_pointer_type(ptr, prop); - search_id_collection(ptype, &sptr, &searchprop); - searchptr= &sptr; - } - } - - /* turn button into search button */ - if(searchprop) { - but->type= SEARCH_MENU; - but->hardmax= MAX2(but->hardmax, 256); - but->rnasearchpoin= *searchptr; - but->rnasearchprop= searchprop; - but->flag |= UI_ICON_LEFT|UI_TEXT_LEFT; - - uiButSetSearchFunc(but, rna_search_cb, but, NULL, NULL); - } -} - -void uiItemPointerR(uiLayout *layout, char *name, int icon, struct PointerRNA *ptr, char *propname, struct PointerRNA *searchptr, char *searchpropname) -{ - PropertyRNA *prop, *searchprop; - PropertyType type; - uiBut *but; - uiBlock *block; - StructRNA *icontype; - int w, h; - - /* validate arguments */ - if(!ptr->data || !searchptr->data) - return; - - prop= RNA_struct_find_property(ptr, propname); - - if(!prop) { - printf("uiItemPointerR: property not found: %s\n", propname); - return; - } - - type= RNA_property_type(prop); - if(!ELEM(type, PROP_POINTER, PROP_STRING)) { - printf("uiItemPointerR: property %s must be a pointer or string.\n", propname); - return; - } - - searchprop= RNA_struct_find_property(searchptr, searchpropname); - - if(!searchprop || RNA_property_type(searchprop) != PROP_COLLECTION) { - printf("uiItemPointerR: search collection property not found: %s\n", searchpropname); - return; - } - - /* get icon & name */ - if(!icon) { - if(type == PROP_POINTER) - icontype= RNA_property_pointer_type(ptr, prop); - else - icontype= RNA_property_pointer_type(searchptr, searchprop); - - icon= RNA_struct_ui_icon(icontype); - } - if(!name) - name= (char*)RNA_property_ui_name(prop); - - /* create button */ - block= uiLayoutGetBlock(layout); - - ui_item_rna_size(layout, name, icon, prop, 0, &w, &h); - but= ui_item_with_label(layout, block, name, icon, ptr, prop, 0, 0, 0, w, h); - - ui_but_add_search(but, ptr, prop, searchptr, searchprop); -} - /* menu item */ static void ui_item_menutype_func(bContext *C, uiLayout *layout, void *arg_mt) { @@ -1411,6 +1267,7 @@ static void ui_litem_layout_box(uiLayout *litem) h= litem->h; litem->x += style->boxspace; + litem->y -= style->boxspace; if(w != 0) litem->w -= 2*style->boxspace; if(h != 0) litem->h -= 2*style->boxspace; @@ -1491,7 +1348,6 @@ static void ui_litem_estimate_column_flow(uiLayout *litem) } } - litem->w= x; litem->h= litem->y - miny; } @@ -1597,9 +1453,9 @@ static void ui_litem_layout_free(uiLayout *litem) totw -= minx; toth -= miny; - if(litem->w && totw > 0) + if(litem->w && totw > litem->w) scalex= (float)litem->w/(float)totw; - if(litem->h && toth > 0) + if(litem->h && toth > litem->h) scaley= (float)litem->h/(float)toth; x= litem->x; @@ -1610,15 +1466,15 @@ static void ui_litem_layout_free(uiLayout *litem) ui_item_size(item, &itemw, &itemh); if(scalex != 1.0f) { - newx= (itemx - minx)*scalex; - itemw= (itemx - minx + itemw)*scalex - newx; - itemx= minx + newx; + newx= itemx*scalex; + itemw= (itemx + itemw)*scalex - newx; + itemx= newx; } if(scaley != 1.0f) { - newy= (itemy - miny)*scaley; - itemh= (itemy - miny + itemh)*scaley - newy; - itemy= miny + newy; + newy= itemy*scaley; + itemh= (itemy + itemh)*scaley - newy; + itemy= newy; } ui_item_position(item, x+itemx-minx, y+itemy-miny, itemw, itemh); diff --git a/source/blender/editors/interface/interface_panel.c b/source/blender/editors/interface/interface_panel.c index eaf78ae89ef..72076175ad5 100644 --- a/source/blender/editors/interface/interface_panel.c +++ b/source/blender/editors/interface/interface_panel.c @@ -104,7 +104,7 @@ static int panel_aligned(ScrArea *sa, ARegion *ar) SpaceButs *sbuts= sa->spacedata.first; return sbuts->align; } - else if(ELEM(ar->regiontype, RGN_TYPE_UI, RGN_TYPE_TOOLS)) + else if(ar->regiontype==RGN_TYPE_UI) return BUT_VERTICAL; return 0; @@ -1288,7 +1288,6 @@ int ui_handler_panel_region(bContext *C, wmEvent *event) /**************** window level modal panel interaction **************/ -/* note, this is modal handler and should not swallow events for animation */ static int ui_handler_panel(bContext *C, wmEvent *event, void *userdata) { Panel *panel= userdata; @@ -1304,6 +1303,8 @@ static int ui_handler_panel(bContext *C, wmEvent *event, void *userdata) panel_activate_state(C, panel, PANEL_STATE_ANIMATION); else panel_activate_state(C, panel, PANEL_STATE_EXIT); + + return WM_UI_HANDLER_BREAK; } else if(event->type == MOUSEMOVE) { if(data->state == PANEL_STATE_WAIT_UNTAB) diff --git a/source/blender/editors/interface/interface_regions.c b/source/blender/editors/interface/interface_regions.c index 49e3abf4d0c..32bcae77e6b 100644 --- a/source/blender/editors/interface/interface_regions.c +++ b/source/blender/editors/interface/interface_regions.c @@ -40,7 +40,6 @@ #include "BLI_dynstr.h" #include "BKE_context.h" -#include "BKE_icons.h" #include "BKE_report.h" #include "BKE_screen.h" #include "BKE_texture.h" @@ -182,7 +181,7 @@ MenuData *decompose_menu_string(char *str) *s= '\0'; s++; } - } else if (c=='|' || c == '\n' || c=='\0') { + } else if (c=='|' || c=='\0') { if (nitem) { *s= '\0'; @@ -434,10 +433,7 @@ struct uiSearchItems { char **names; void **pointers; - int *icons; - - AutoComplete *autocpl; - void *active; + }; typedef struct uiSearchboxData { @@ -452,21 +448,8 @@ typedef struct uiSearchboxData { /* exported for use by search callbacks */ /* returns zero if nothing to add */ -int uiSearchItemAdd(uiSearchItems *items, const char *name, void *poin, int iconid) +int uiSearchItemAdd(uiSearchItems *items, const char *name, void *poin) { - /* hijack for autocomplete */ - if(items->autocpl) { - autocomplete_do_name(items->autocpl, name); - return 1; - } - - /* hijack for finding active item */ - if(items->active) { - if(poin==items->active) - items->offset_i= items->totitem; - items->totitem++; - return 1; - } if(items->totitem>=items->maxitem) { items->more= 1; @@ -481,7 +464,6 @@ int uiSearchItemAdd(uiSearchItems *items, const char *name, void *poin, int icon BLI_strncpy(items->names[items->totitem], name, items->maxstrlen); items->pointers[items->totitem]= poin; - items->icons[items->totitem]= iconid; items->totitem++; @@ -606,52 +588,20 @@ void ui_searchbox_update(bContext *C, ARegion *ar, uiBut *but, int reset) /* reset vars */ data->items.totitem= 0; data->items.more= 0; - if(reset==0) { + if(reset==0) data->items.offset_i= data->items.offset; - } else { data->items.offset_i= data->items.offset= 0; data->active= 0; - - /* handle active */ - if(but->search_func && but->func_arg2) { - data->items.active= but->func_arg2; - but->search_func(C, but->search_arg, but->editstr, &data->items); - data->items.active= NULL; - - /* found active item, calculate real offset by centering it */ - if(data->items.totitem) { - /* first case, begin of list */ - if(data->items.offset_i < data->items.maxitem) { - data->active= data->items.offset_i+1; - data->items.offset_i= 0; - } - else { - /* second case, end of list */ - if(data->items.totitem - data->items.offset_i <= data->items.maxitem) { - data->active= 1 + data->items.offset_i - data->items.totitem + data->items.maxitem; - data->items.offset_i= data->items.totitem - data->items.maxitem; - } - else { - /* center active item */ - data->items.offset_i -= data->items.maxitem/2; - data->active= 1 + data->items.maxitem/2; - } - } - } - data->items.offset= data->items.offset_i; - data->items.totitem= 0; - } } /* callback */ if(but->search_func) but->search_func(C, but->search_arg, but->editstr, &data->items); - /* handle case where editstr is equal to one of items */ - if(reset && data->active==0) { + if(reset) { int a; - + /* handle case where editstr is equal to one of items */ for(a=0; a<data->items.totitem; a++) { char *cpoin= strchr(data->items.names[a], '|'); @@ -670,18 +620,6 @@ void ui_searchbox_update(bContext *C, ARegion *ar, uiBut *but, int reset) ED_region_tag_redraw(ar); } -void ui_searchbox_autocomplete(bContext *C, ARegion *ar, uiBut *but, char *str) -{ - uiSearchboxData *data= ar->regiondata; - - data->items.autocpl= autocomplete_begin(str, ui_get_but_string_max_length(but)); - - but->search_func(C, but->search_arg, but->editstr, &data->items); - - autocomplete_end(data->items.autocpl, str); - data->items.autocpl= NULL; -} - static void ui_searchbox_region_draw(const bContext *C, ARegion *ar) { uiSearchboxData *data= ar->regiondata; @@ -701,21 +639,18 @@ static void ui_searchbox_region_draw(const bContext *C, ARegion *ar) for(a=0; a<data->items.totitem; a++) { ui_searchbox_butrect(&rect, data, a); - /* widget itself */ - ui_draw_menu_item(&data->fstyle, &rect, data->items.names[a], data->items.icons[a], (a+1)==data->active?UI_ACTIVE:0); + ui_draw_menu_item(&data->fstyle, &rect, data->items.names[a], (a+1)==data->active?UI_ACTIVE:0); } /* indicate more */ if(data->items.more) { - ui_searchbox_butrect(&rect, data, data->items.maxitem-1); glEnable(GL_BLEND); - UI_icon_draw((rect.xmax-rect.xmin)/2, rect.ymin-9, ICON_TRIA_DOWN); + UI_icon_draw((data->bbox.xmax-data->bbox.xmin)/2, 8, ICON_TRIA_DOWN); glDisable(GL_BLEND); } if(data->items.offset) { - ui_searchbox_butrect(&rect, data, 0); glEnable(GL_BLEND); - UI_icon_draw((rect.xmax-rect.xmin)/2, rect.ymax-7, ICON_TRIA_UP); + UI_icon_draw((data->bbox.xmax-data->bbox.xmin)/2, data->bbox.ymax-13, ICON_TRIA_UP); glDisable(GL_BLEND); } } @@ -731,7 +666,6 @@ static void ui_searchbox_region_free(ARegion *ar) MEM_freeN(data->items.names[a]); MEM_freeN(data->items.names); MEM_freeN(data->items.pointers); - MEM_freeN(data->items.icons); MEM_freeN(data); ar->regiondata= NULL; @@ -745,7 +679,7 @@ ARegion *ui_searchbox_create(bContext *C, ARegion *butregion, uiBut *but) uiSearchboxData *data; float aspect= but->block->aspect; float x1f, x2f, y1f, y2f; - int x1, x2, y1, y2, winx, winy, ofsx, ofsy; + int x1, x2, y1, y2, winx, winy; /* create area region */ ar= ui_add_temporary_region(CTX_wm_screen(C)); @@ -798,14 +732,6 @@ ARegion *ui_searchbox_create(bContext *C, ARegion *butregion, uiBut *but) x2f= but->x2 + 5; /* symmetrical */ y2f= but->y1; y1f= y2f - uiSearchBoxhHeight(); - - ofsx= (but->block->panel)? but->block->panel->ofsx: 0; - ofsy= (but->block->panel)? but->block->panel->ofsy: 0; - - x1f += ofsx; - x2f += ofsx; - y1f += ofsy; - y2f += ofsy; /* minimal width */ if(x2f - x1f < 150) x2f= x1f+150; // XXX arbitrary @@ -868,7 +794,6 @@ ARegion *ui_searchbox_create(bContext *C, ARegion *butregion, uiBut *but) data->items.totitem= 0; data->items.names= MEM_callocN(SEARCH_ITEMS*sizeof(void *), "search names"); data->items.pointers= MEM_callocN(SEARCH_ITEMS*sizeof(void *), "search pointers"); - data->items.icons= MEM_callocN(SEARCH_ITEMS*sizeof(int), "search icons"); for(x1=0; x1<SEARCH_ITEMS; x1++) data->items.names[x1]= MEM_callocN(but->hardmax+1, "search pointers"); @@ -1795,118 +1720,24 @@ static void do_picker_small_cb(bContext *C, void *bt1, void *hsv1) popup->menuretval= UI_RETURN_UPDATE; } -/* picker sizes S hsize, F full size, D spacer, B button/pallette height */ -#define SPICK1 150.0 -#define DPICK1 6.0 -/* only the color, a HS circle and V slider */ -static void uiBlockPickerSmall(uiBlock *block, float *col, float *hsv, float *old, char *hexcol, char mode, short retval) +/* only the color, a circle, slider */ +void uiBlockPickerSmall(uiBlock *block, float *col, float *hsv, float *old, char *hexcol, char mode, short retval) { uiBut *bt; VECCOPY(old, col); // old color stored there, for palette_cb to work /* HS circle */ - bt= uiDefButF(block, HSVCIRCLE, retval, "", 0, 0,SPICK1,SPICK1, col, 0.0, 0.0, 0, 0, ""); + bt= uiDefButF(block, HSVCIRCLE, retval, "", 0, 0,SPICK,SPICK, col, 0.0, 0.0, 0, 0, ""); uiButSetFunc(bt, do_picker_small_cb, bt, hsv); /* value */ - bt= uiDefButF(block, HSVCUBE, retval, "", SPICK1+DPICK1,0,14,SPICK1, col, 0.0, 0.0, 4, 0, ""); - uiButSetFunc(bt, do_picker_small_cb, bt, hsv); -} - - -static void picker_new_hide_reveal(uiBlock *block, short colormode) -{ - uiBut *bt; - - /* tag buttons */ - for(bt= block->buttons.first; bt; bt= bt->next) { - - if(bt->type==NUMSLI || bt->type==TEX) { - if( bt->str[1]=='e') { - if(colormode==2) bt->flag &= ~UI_HIDDEN; - else bt->flag |= UI_HIDDEN; - } - else if( ELEM3(bt->str[0], 'R', 'G', 'B')) { - if(colormode==0) bt->flag &= ~UI_HIDDEN; - else bt->flag |= UI_HIDDEN; - } - else if( ELEM3(bt->str[0], 'H', 'S', 'V')) { - if(colormode==1) bt->flag &= ~UI_HIDDEN; - else bt->flag |= UI_HIDDEN; - } - } - } -} - -static void do_picker_new_mode_cb(bContext *C, void *bt1, void *colv) -{ - uiBut *bt= bt1; - short colormode= ui_get_but_val(bt); - - picker_new_hide_reveal(bt->block, colormode); -} - - -/* a HS circle, V slider, rgb/hsv/hex sliders */ -static void uiBlockPickerNew(uiBlock *block, float *col, float *hsv, float *old, char *hexcol, char mode, short retval) -{ - static short colormode= 0; /* temp? 0=rgb, 1=hsv, 2=hex */ - uiBut *bt; - int width; - - VECCOPY(old, col); // old color stored there, for palette_cb to work - - /* HS circle */ - bt= uiDefButF(block, HSVCIRCLE, retval, "", 0, 0,SPICK1,SPICK1, col, 0.0, 0.0, 0, 0, ""); - uiButSetFunc(bt, do_picker_small_cb, bt, hsv); - - /* value */ - bt= uiDefButF(block, HSVCUBE, retval, "", SPICK1+DPICK1,0,14,SPICK1, col, 0.0, 0.0, 4, 0, ""); + bt= uiDefButF(block, HSVCUBE, retval, "", SPICK+DPICK,0,14,SPICK, col, 0.0, 0.0, 4, 0, ""); uiButSetFunc(bt, do_picker_small_cb, bt, hsv); - - /* mode */ - width= (SPICK1+DPICK1+14)/3; - uiBlockBeginAlign(block); - bt= uiDefButS(block, ROW, retval, "RGB", 0, -30, width, 19, &colormode, 0.0, 0.0, 0, 0, ""); - uiButSetFunc(bt, do_picker_new_mode_cb, bt, col); - bt= uiDefButS(block, ROW, retval, "HSV", width, -30, width, 19, &colormode, 0.0, 1.0, 0, 0, ""); - uiButSetFunc(bt, do_picker_new_mode_cb, bt, hsv); - bt= uiDefButS(block, ROW, retval, "Hex", 2*width, -30, width, 19, &colormode, 0.0, 2.0, 0, 0, ""); - uiButSetFunc(bt, do_picker_new_mode_cb, bt, hexcol); - uiBlockEndAlign(block); - - /* sliders or hex */ - width= (SPICK1+DPICK1+14); - rgb_to_hsv(col[0], col[1], col[2], hsv, hsv+1, hsv+2); - sprintf(hexcol, "%02X%02X%02X", (unsigned int)(col[0]*255.0), (unsigned int)(col[1]*255.0), (unsigned int)(col[2]*255.0)); - uiBlockBeginAlign(block); - bt= uiDefButF(block, NUMSLI, 0, "R ", 0, -60, width, 19, col, 0.0, 1.0, 10, 3, ""); - uiButSetFunc(bt, do_palette1_cb, bt, hsv); - bt= uiDefButF(block, NUMSLI, 0, "G ", 0, -80, width, 19, col+1, 0.0, 1.0, 10, 3, ""); - uiButSetFunc(bt, do_palette1_cb, bt, hsv); - bt= uiDefButF(block, NUMSLI, 0, "B ", 0, -100, width, 19, col+2, 0.0, 1.0, 10, 3, ""); - uiButSetFunc(bt, do_palette1_cb, bt, hsv); - uiBlockEndAlign(block); - - uiBlockBeginAlign(block); - bt= uiDefButF(block, NUMSLI, 0, "H ", 0, -60, width, 19, hsv, 0.0, 1.0, 10, 3, ""); - uiButSetFunc(bt, do_palette2_cb, bt, col); - bt= uiDefButF(block, NUMSLI, 0, "S ", 0, -80, width, 19, hsv+1, 0.0, 1.0, 10, 3, ""); - uiButSetFunc(bt, do_palette2_cb, bt, col); - bt= uiDefButF(block, NUMSLI, 0, "V ", 0, -100, width, 19, hsv+2, 0.0, 1.0, 10, 3, ""); - uiButSetFunc(bt, do_palette2_cb, bt, col); - uiBlockEndAlign(block); - - bt= uiDefBut(block, TEX, 0, "Hex: ", 0, -80, width, 19, hexcol, 0, 8, 0, 0, "Hex triplet for color (#RRGGBB)"); - uiButSetFunc(bt, do_palette_hex_cb, bt, hexcol); - - picker_new_hide_reveal(block, colormode); } - static int ui_picker_small_wheel(const bContext *C, uiBlock *block, wmEvent *event) { float add= 0.0f; @@ -1959,22 +1790,13 @@ uiBlock *ui_block_func_COL(bContext *C, uiPopupBlockHandle *handle, void *arg_bu block->flag= UI_BLOCK_LOOP|UI_BLOCK_REDRAW|UI_BLOCK_KEEP_OPEN; uiBoundsBlock(block, 3); } - else if(win->eventstate->alt) { + else { uiBlockPickerSmall(block, handle->retvec, hsvcol, oldcol, hexcol, 'p', 0); block->flag= UI_BLOCK_LOOP|UI_BLOCK_REDRAW|UI_BLOCK_RET_1|UI_BLOCK_OUT_1; uiBoundsBlock(block, 10); block->block_event_func= ui_picker_small_wheel; - } - else { - uiBlockPickerNew(block, handle->retvec, hsvcol, oldcol, hexcol, 'p', 0); - block->flag= UI_BLOCK_LOOP|UI_BLOCK_REDRAW|UI_BLOCK_KEEP_OPEN; - uiBoundsBlock(block, 10); - - block->block_event_func= ui_picker_small_wheel; - } - - + } /* and lets go */ block->direction= UI_TOP; @@ -2642,6 +2464,7 @@ static uiPopupBlockHandle *ui_pup_menu(bContext *C, int maxrow, uiMenuHandleFunc return menu; } + static void operator_name_cb(bContext *C, void *arg, int retval) { const char *opname= arg; diff --git a/source/blender/editors/interface/interface_style.c b/source/blender/editors/interface/interface_style.c index e8fba38f793..831a8a5bf6c 100644 --- a/source/blender/editors/interface/interface_style.c +++ b/source/blender/editors/interface/interface_style.c @@ -92,7 +92,6 @@ static uiStyle *ui_style_new(ListBase *styles, const char *name) style->paneltitle.uifont_id= UIFONT_DEFAULT; style->paneltitle.points= 13; style->paneltitle.kerning= 0.0; - style->paneltitle.overlap= 0; style->paneltitle.shadow= 5; style->paneltitle.shadx= 2; style->paneltitle.shady= -2; @@ -102,7 +101,6 @@ static uiStyle *ui_style_new(ListBase *styles, const char *name) style->grouplabel.uifont_id= UIFONT_DEFAULT; style->grouplabel.points= 12; style->grouplabel.kerning= 0.0; - style->grouplabel.overlap= 0; style->grouplabel.shadow= 3; style->grouplabel.shadx= 1; style->grouplabel.shady= -1; @@ -111,7 +109,6 @@ static uiStyle *ui_style_new(ListBase *styles, const char *name) style->widgetlabel.uifont_id= UIFONT_DEFAULT; style->widgetlabel.points= 11; style->widgetlabel.kerning= 0.0; - style->widgetlabel.overlap= 0; style->widgetlabel.shadow= 3; style->widgetlabel.shadx= 1; style->widgetlabel.shady= -1; @@ -148,6 +145,22 @@ static uiFont *uifont_to_blfont(int id) /* *************** draw ************************ */ +static void ui_font_shadow_draw(uiFontStyle *fs, int x, int y, char *str) +{ + float color[4]; + + glGetFloatv(GL_CURRENT_COLOR, color); + + glColor4f(fs->shadowcolor, fs->shadowcolor, fs->shadowcolor, fs->shadowalpha); + + BLF_blur(fs->shadow); + BLF_position(x+fs->shadx, y+fs->shady, 0.0f); + BLF_draw(str); + BLF_blur(0); + + glColor4fv(color); +} + void uiStyleFontDraw(uiFontStyle *fs, rcti *rect, char *str) { float height; @@ -166,23 +179,14 @@ void uiStyleFontDraw(uiFontStyle *fs, rcti *rect, char *str) /* clip is very strict, so we give it some space */ BLF_clipping(rect->xmin-1, rect->ymin-4, rect->xmax+1, rect->ymax+4); BLF_enable(BLF_CLIPPING); + + if(fs->shadow) + ui_font_shadow_draw(fs, rect->xmin+xofs, rect->ymin+yofs, str); + BLF_position(rect->xmin+xofs, rect->ymin+yofs, 0.0f); - - if (fs->shadow) { - BLF_enable(BLF_SHADOW); - BLF_shadow(fs->shadow, fs->shadowcolor, fs->shadowcolor, fs->shadowcolor, fs->shadowalpha); - BLF_shadow_offset(fs->shadx, fs->shady); - } - - if (fs->overlap) - BLF_enable(BLF_OVERLAP_CHAR); - BLF_draw(str); + BLF_disable(BLF_CLIPPING); - if (fs->shadow) - BLF_disable(BLF_SHADOW); - if (fs->overlap) - BLF_disable(BLF_OVERLAP_CHAR); } /* ************** helpers ************************ */ diff --git a/source/blender/editors/interface/interface_templates.c b/source/blender/editors/interface/interface_templates.c index b128da7b97f..15c0619e4e1 100644 --- a/source/blender/editors/interface/interface_templates.c +++ b/source/blender/editors/interface/interface_templates.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: interface_templates.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -27,14 +27,9 @@ #include "MEM_guardedalloc.h" -#include "DNA_scene_types.h" -#include "DNA_screen_types.h" - #include "BLI_string.h" #include "BKE_context.h" -#include "BKE_icons.h" -#include "BKE_global.h" #include "BKE_library.h" #include "BKE_utildefines.h" @@ -48,7 +43,6 @@ #include "UI_interface.h" #include "UI_resources.h" -#include "interface_intern.h" void ui_template_fix_linking() { @@ -64,55 +58,107 @@ void uiTemplateHeader(uiLayout *layout, bContext *C) ED_area_header_standardbuttons(C, block, 0); } -/********************** Search Callbacks *************************/ +/******************* Header ID Template ************************/ typedef struct TemplateID { PointerRNA ptr; PropertyRNA *prop; - ListBase *idlb; + int flag; + short browse; + + char newop[256]; + char openop[256]; + char unlinkop[256]; + + short idtype; } TemplateID; -/* Search browse menu, assign */ -static void id_search_call_cb(struct bContext *C, void *arg_template, void *item) +static void template_id_cb(bContext *C, void *arg_litem, void *arg_event) { - TemplateID *template= (TemplateID*)arg_template; + TemplateID *template= (TemplateID*)arg_litem; + PointerRNA idptr= RNA_property_pointer_get(&template->ptr, template->prop); + ID *id= idptr.data; + int event= GET_INT_FROM_POINTER(arg_event); + + if(event == UI_ID_BROWSE && template->browse == 32767) + event= UI_ID_ADD_NEW; + else if(event == UI_ID_BROWSE && template->browse == 32766) + event= UI_ID_OPEN; + + switch(event) { + case UI_ID_BROWSE: + printf("warning, id browse shouldnt come here\n"); + break; + case UI_ID_DELETE: + memset(&idptr, 0, sizeof(idptr)); + RNA_property_pointer_set(&template->ptr, template->prop, idptr); + RNA_property_update(C, &template->ptr, template->prop); + break; + case UI_ID_FAKE_USER: + if(id) { + if(id->flag & LIB_FAKEUSER) id->us++; + else id->us--; + } + else return; + break; + case UI_ID_PIN: + break; + case UI_ID_ADD_NEW: + WM_operator_name_call(C, template->newop, WM_OP_INVOKE_REGION_WIN, NULL); + break; + case UI_ID_OPEN: + WM_operator_name_call(C, template->openop, WM_OP_INVOKE_REGION_WIN, NULL); + break; +#if 0 + case UI_ID_ALONE: + if(!id || id->us < 1) + return; + break; + case UI_ID_LOCAL: + if(!id || id->us < 1) + return; + break; + case UI_ID_AUTO_NAME: + break; +#endif + } +} - /* ID */ +/* ID Search browse menu, assign */ +static void id_search_call_cb(struct bContext *C, void *arg_litem, void *item) +{ if(item) { - PointerRNA idptr; + TemplateID *template= (TemplateID*)arg_litem; + PointerRNA idptr= RNA_property_pointer_get(&template->ptr, template->prop); RNA_id_pointer_create(item, &idptr); RNA_property_pointer_set(&template->ptr, template->prop, idptr); RNA_property_update(C, &template->ptr, template->prop); - } + } } /* ID Search browse menu, do the search */ -static void id_search_cb(const struct bContext *C, void *arg_template, char *str, uiSearchItems *items) +static void id_search_cb(const struct bContext *C, void *arg_litem, char *str, uiSearchItems *items) { - TemplateID *template= (TemplateID*)arg_template; - Scene *scene= CTX_data_scene(C); - ListBase *lb= template->idlb; + TemplateID *template= (TemplateID*)arg_litem; + ListBase *lb= wich_libbase(CTX_data_main(C), template->idtype); ID *id; - int iconid; - - /* ID listbase */ + for(id= lb->first; id; id= id->next) { - iconid= ui_id_icon_get(scene, id); - - if(BLI_strcasestr(id->name+2, str)) - if(!uiSearchItemAdd(items, id->name+2, id, iconid)) + + if(BLI_strcasestr(id->name+2, str)) { + if(0==uiSearchItemAdd(items, id->name+2, id)) break; + } } } /* ID Search browse menu, open */ -static uiBlock *search_menu(bContext *C, ARegion *ar, void *arg_litem) +static uiBlock *id_search_menu(bContext *C, ARegion *ar, void *arg_litem) { static char search[256]; static TemplateID template; - PointerRNA idptr; wmEvent event; wmWindow *win= CTX_wm_window(C); uiBlock *block; @@ -123,9 +169,6 @@ static uiBlock *search_menu(bContext *C, ARegion *ar, void *arg_litem) /* arg_litem is malloced, can be freed by parent button */ template= *((TemplateID*)arg_litem); - /* get active id for showing first item */ - idptr= RNA_property_pointer_get(&template.ptr, template.prop); - block= uiBeginBlock(C, ar, "_popup", UI_EMBOSS); uiBlockSetFlag(block, UI_BLOCK_LOOP|UI_BLOCK_REDRAW|UI_BLOCK_RET_1); @@ -133,7 +176,7 @@ static uiBlock *search_menu(bContext *C, ARegion *ar, void *arg_litem) uiDefBut(block, LABEL, 0, "", 10, 15, 150, uiSearchBoxhHeight(), NULL, 0, 0, 0, 0, NULL); but= uiDefSearchBut(block, search, 0, ICON_VIEWZOOM, 256, 10, 0, 150, 19, ""); - uiButSetSearchFunc(but, id_search_cb, &template, id_search_call_cb, idptr.data); + uiButSetSearchFunc(but, id_search_cb, &template, id_search_call_cb); uiBoundsBlock(block, 6); uiBlockSetDirection(block, UI_DOWN); @@ -149,57 +192,17 @@ static uiBlock *search_menu(bContext *C, ARegion *ar, void *arg_litem) return block; } -/************************ ID Template ***************************/ +/* ****************** */ -static void template_id_cb(bContext *C, void *arg_litem, void *arg_event) -{ - TemplateID *template= (TemplateID*)arg_litem; - PointerRNA idptr= RNA_property_pointer_get(&template->ptr, template->prop); - ID *id= idptr.data; - int event= GET_INT_FROM_POINTER(arg_event); - - switch(event) { - case UI_ID_BROWSE: - case UI_ID_PIN: - case UI_ID_OPEN: - case UI_ID_ADD_NEW: - printf("warning, id event %d shouldnt come here\n", event); - break; - case UI_ID_DELETE: - memset(&idptr, 0, sizeof(idptr)); - RNA_property_pointer_set(&template->ptr, template->prop, idptr); - RNA_property_update(C, &template->ptr, template->prop); - break; - case UI_ID_FAKE_USER: - if(id) { - if(id->flag & LIB_FAKEUSER) id->us++; - else id->us--; - } - else return; - break; -#if 0 - case UI_ID_ALONE: - if(!id || id->us < 1) - return; - break; - case UI_ID_LOCAL: - if(!id || id->us < 1) - return; - break; - case UI_ID_AUTO_NAME: - break; -#endif - } -} -static void template_ID(bContext *C, uiBlock *block, TemplateID *template, StructRNA *type, int flag, char *newop, char *unlinkop) +static void template_header_ID(bContext *C, uiBlock *block, TemplateID *template, StructRNA *type) { uiBut *but; PointerRNA idptr; ListBase *lb; idptr= RNA_property_pointer_get(&template->ptr, template->prop); - lb= template->idlb; + lb= wich_libbase(CTX_data_main(C), template->idtype); if(idptr.type) type= idptr.type; @@ -207,8 +210,29 @@ static void template_ID(bContext *C, uiBlock *block, TemplateID *template, Struc uiDefIconBut(block, LABEL, 0, RNA_struct_ui_icon(type), 0, 0, UI_UNIT_X, UI_UNIT_Y, NULL, 0.0, 0.0, 0, 0, ""); uiBlockBeginAlign(block); - if(flag & UI_ID_BROWSE) - uiDefBlockButN(block, search_menu, MEM_dupallocN(template), "", 0, 0, UI_UNIT_X, UI_UNIT_Y, "Browse ID data"); + if(template->flag & UI_ID_BROWSE) { + /* + char *extrastr, *str; + + if((template->flag & UI_ID_ADD_NEW) && (template->flag & UI_ID_OPEN)) + extrastr= "OPEN NEW %x 32766 |ADD NEW %x 32767"; + else if(template->flag & UI_ID_ADD_NEW) + extrastr= "ADD NEW %x 32767"; + else if(template->flag & UI_ID_OPEN) + extrastr= "OPEN NEW %x 32766"; + else + extrastr= NULL; + + duptemplate= MEM_dupallocN(template); + IDnames_to_pupstring(&str, NULL, extrastr, lb, idptr.data, &duptemplate->browse); + + but= uiDefButS(block, MENU, 0, str, 0, 0, UI_UNIT_X, UI_UNIT_Y, &duptemplate->browse, 0, 0, 0, 0, "Browse existing choices, or add new"); + uiButSetNFunc(but, template_id_cb, duptemplate, SET_INT_IN_POINTER(UI_ID_BROWSE)); + + MEM_freeN(str); + */ + uiDefBlockButN(block, id_search_menu, MEM_dupallocN(template), "", 0, 0, UI_UNIT_X, UI_UNIT_Y, "Browse ID data"); + } /* text button with name */ if(idptr.data) { @@ -220,11 +244,11 @@ static void template_ID(bContext *C, uiBlock *block, TemplateID *template, Struc uiButSetNFunc(but, template_id_cb, MEM_dupallocN(template), SET_INT_IN_POINTER(UI_ID_RENAME)); } - if(flag & UI_ID_ADD_NEW) { + if(template->flag & UI_ID_ADD_NEW) { int w= idptr.data?UI_UNIT_X:UI_UNIT_X*6; - if(newop) { - but= uiDefIconTextButO(block, BUT, newop, WM_OP_EXEC_REGION_WIN, ICON_ZOOMIN, "Add New", 0, 0, w, UI_UNIT_Y, NULL); + if(template->newop[0]) { + but= uiDefIconTextButO(block, BUT, template->newop, WM_OP_EXEC_REGION_WIN, ICON_ZOOMIN, "Add New", 0, 0, w, UI_UNIT_Y, NULL); } else { but= uiDefIconTextBut(block, BUT, 0, ICON_ZOOMIN, "Add New", 0, 0, w, UI_UNIT_Y, NULL, 0, 0, 0, 0, NULL); @@ -233,9 +257,9 @@ static void template_ID(bContext *C, uiBlock *block, TemplateID *template, Struc } /* delete button */ - if(idptr.data && (flag & UI_ID_DELETE)) { - if(unlinkop) { - but= uiDefIconButO(block, BUT, unlinkop, WM_OP_EXEC_REGION_WIN, ICON_X, 0, 0, UI_UNIT_X, UI_UNIT_Y, NULL); + if(idptr.data && (template->flag & UI_ID_DELETE)) { + if(template->unlinkop[0]) { + but= uiDefIconButO(block, BUT, template->unlinkop, WM_OP_EXEC_REGION_WIN, ICON_X, 0, 0, UI_UNIT_X, UI_UNIT_Y, NULL); } else { but= uiDefIconBut(block, BUT, 0, ICON_X, 0, 0, UI_UNIT_X, UI_UNIT_Y, NULL, 0, 0, 0, 0, NULL); @@ -246,13 +270,12 @@ static void template_ID(bContext *C, uiBlock *block, TemplateID *template, Struc uiBlockEndAlign(block); } -void uiTemplateID(uiLayout *layout, bContext *C, PointerRNA *ptr, char *propname, char *newop, char *unlinkop) +void uiTemplateID(uiLayout *layout, bContext *C, PointerRNA *ptr, char *propname, char *newop, char *openop, char *unlinkop) { TemplateID *template; uiBlock *block; PropertyRNA *prop; StructRNA *type; - int flag; if(!ptr->data) return; @@ -267,19 +290,26 @@ void uiTemplateID(uiLayout *layout, bContext *C, PointerRNA *ptr, char *propname template= MEM_callocN(sizeof(TemplateID), "TemplateID"); template->ptr= *ptr; template->prop= prop; + template->flag= UI_ID_BROWSE|UI_ID_RENAME|UI_ID_DELETE; - flag= UI_ID_BROWSE|UI_ID_RENAME|UI_ID_DELETE; - - if(newop) - flag |= UI_ID_ADD_NEW; + if(newop) { + template->flag |= UI_ID_ADD_NEW; + BLI_strncpy(template->newop, newop, sizeof(template->newop)); + } + if(openop) { + template->flag |= UI_ID_OPEN; + BLI_strncpy(template->openop, openop, sizeof(template->openop)); + } + if(unlinkop) + BLI_strncpy(template->unlinkop, unlinkop, sizeof(template->unlinkop)); type= RNA_property_pointer_type(ptr, prop); - template->idlb= wich_libbase(CTX_data_main(C), RNA_type_to_ID_code(type)); + template->idtype = RNA_type_to_ID_code(type); - if(template->idlb) { + if(template->idtype) { uiLayoutRow(layout, 1); block= uiLayoutGetBlock(layout); - template_ID(C, block, template, type, flag, newop, unlinkop); + template_header_ID(C, block, template, type); } MEM_freeN(template); @@ -332,15 +362,6 @@ static void modifiers_del(bContext *C, void *ob_v, void *md_v) BKE_reports_clear(&reports); } -static void modifiers_activate(bContext *C, void *ob_v, void *md_v) -{ - Scene *scene= CTX_data_scene(C); - Object *ob= ob_v; - - WM_event_add_notifier(C, NC_OBJECT|ND_MODIFIER, ob); - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); -} - static void modifiers_moveUp(bContext *C, void *ob_v, void *md_v) { Scene *scene= CTX_data_scene(C); @@ -534,10 +555,7 @@ static uiLayout *draw_modifier(uiLayout *layout, Object *ob, ModifierData *md, i uiBlockSetEmboss(block, UI_EMBOSSN); uiDefIconButBitI(block, ICONTOG, eModifierMode_Expanded, 0, ICON_TRIA_RIGHT, 0, 0, UI_UNIT_X, UI_UNIT_Y, &md->mode, 0.0, 0.0, 0.0, 0.0, "Collapse/Expand Modifier"); } - - /* modifier-type icon */ - uiDefIconBut(block, BUT, 0, RNA_struct_ui_icon(ptr.type), 0, 0, UI_UNIT_X, UI_UNIT_Y, NULL, 0.0, 0.0, 0.0, 0.0, "Current Modifier Type"); - + uiBlockSetEmboss(block, UI_EMBOSS); if (isVirtual) { @@ -548,16 +566,14 @@ static uiLayout *draw_modifier(uiLayout *layout, Object *ob, ModifierData *md, i uiButSetFunc(but, modifiers_convertToReal, ob, md); } else { uiBlockBeginAlign(block); - uiDefBut(block, TEX, 0, "", 0, 0, buttonWidth-40, UI_UNIT_Y, md->name, 0.0, sizeof(md->name)-1, 0.0, 0.0, "Modifier name"); + uiDefBut(block, TEX, 0, "", 0, 0, buttonWidth-60, UI_UNIT_Y, md->name, 0.0, sizeof(md->name)-1, 0.0, 0.0, "Modifier name"); /* Softbody not allowed in this situation, enforce! */ if (((md->type!=eModifierType_Softbody && md->type!=eModifierType_Collision) || !(ob->pd && ob->pd->deflect)) && (md->type!=eModifierType_Surface)) { uiDefIconButBitI(block, TOG, eModifierMode_Render, 0, ICON_SCENE, 0, 0, 19, UI_UNIT_Y,&md->mode, 0, 0, 1, 0, "Enable modifier during rendering"); but= uiDefIconButBitI(block, TOG, eModifierMode_Realtime, 0, ICON_VIEW3D, 0, 0, 19, UI_UNIT_Y,&md->mode, 0, 0, 1, 0, "Enable modifier during interactive display"); - uiButSetFunc(but, modifiers_activate, ob, md); if (mti->flags&eModifierTypeFlag_SupportsEditmode) { - but= uiDefIconButBitI(block, TOG, eModifierMode_Editmode, 0, ICON_EDITMODE_HLT, 0, 0, 19, UI_UNIT_Y,&md->mode, 0, 0, 1, 0, "Enable modifier during Editmode (only if enabled for display)"); - uiButSetFunc(but, modifiers_activate, ob, md); + uiDefIconButBitI(block, TOG, eModifierMode_Editmode, 0, ICON_EDITMODE_HLT, 0, 0, 19, UI_UNIT_Y,&md->mode, 0, 0, 1, 0, "Enable modifier during Editmode (only if enabled for display)"); } } uiBlockEndAlign(block); @@ -1474,209 +1490,3 @@ void uiTemplateLayers(uiLayout *layout, PointerRNA *ptr, char *propname) } } } - - -/************************* List Template **************************/ - -#if 0 -typedef struct ListItem { - PointerRNA ptr; - PropertyRNA *prop; - PropertyRNA *activeprop; - - PointerRNA activeptr; - int activei; - - int selected; -} ListItem; - -static void list_item_cb(bContext *C, void *arg_item, void *arg_unused) -{ - ListItem *item= (ListItem*)arg_item; - PropertyType activetype; - char *activename; - - if(item->selected) { - activetype= RNA_property_type(item->activeprop); - - if(activetype == PROP_POINTER) - RNA_property_pointer_set(&item->ptr, item->activeprop, item->activeptr); - else if(activetype == PROP_INT) - RNA_property_int_set(&item->ptr, item->activeprop, item->activei); - else if(activetype == PROP_STRING) { - activename= RNA_struct_name_get_alloc(&item->activeptr, NULL, 0); - RNA_property_string_set(&item->ptr, item->activeprop, activename); - MEM_freeN(activename); - } - } -} -#endif - -ListBase uiTemplateList(uiLayout *layout, PointerRNA *ptr, char *propname, char *activepropname, int rows, int columns, int compact) -{ - CollectionPointerLink *link; - PropertyRNA *prop, *activeprop; - PropertyType type, activetype; - PointerRNA activeptr; - uiLayout *box, *row, *col; - uiBlock *block; - uiBut *but; - ListBase lb; - char *name, *activename= NULL, str[32]; - int i= 1, activei= 0, len, items, found; - static int scroll = 1; - - lb.first= lb.last= NULL; - - /* validate arguments */ - if(!ptr->data) - return lb; - - prop= RNA_struct_find_property(ptr, propname); - if(!prop) { - printf("uiTemplateList: property not found: %s\n", propname); - return lb; - } - - activeprop= RNA_struct_find_property(ptr, activepropname); - if(!activeprop) { - printf("uiTemplateList: property not found: %s\n", activepropname); - return lb; - } - - type= RNA_property_type(prop); - if(type != PROP_COLLECTION) { - printf("uiTemplateList: expected collection property.\n"); - return lb; - } - - activetype= RNA_property_type(activeprop); - if(!ELEM3(activetype, PROP_POINTER, PROP_INT, PROP_STRING)) { - printf("uiTemplateList: expected pointer, integer or string property.\n"); - return lb; - } - - /* get active data */ - if(activetype == PROP_POINTER) - activeptr= RNA_property_pointer_get(ptr, activeprop); - else if(activetype == PROP_INT) - activei= RNA_property_int_get(ptr, activeprop); - else if(activetype == PROP_STRING) - activename= RNA_property_string_get_alloc(ptr, activeprop, NULL, 0); - - block= uiLayoutGetBlock(layout); - - if(compact) { - /* compact layout */ - found= 0; - - row= uiLayoutRow(layout, 1); - - RNA_PROP_BEGIN(ptr, itemptr, prop) { - if(activetype == PROP_POINTER) - found= (activeptr.data == itemptr.data); - else if(activetype == PROP_INT) - found= (activei == i); - else if(activetype == PROP_STRING) - found= (strcmp(activename, name) == 0); - - if(found) { - name= RNA_struct_name_get_alloc(&itemptr, NULL, 0); - if(name) { - uiItemL(row, name, RNA_struct_ui_icon(itemptr.type)); - MEM_freeN(name); - } - - link= MEM_callocN(sizeof(CollectionPointerLink), "uiTemplateList return"); - link->ptr= itemptr; - BLI_addtail(&lb, link); - } - - i++; - } - RNA_PROP_END; - - if(i == 1) - uiItemL(row, "", 0); - - sprintf(str, "%d :", i-1); - but= uiDefIconTextButR(block, NUM, 0, 0, str, 0,0,UI_UNIT_X*5,UI_UNIT_Y, ptr, activepropname, 0, 0, 0, 0, 0, ""); - if(i == 1) - uiButSetFlag(but, UI_BUT_DISABLED); - } - else { - if(rows == 0) - rows= 5; - if(columns == 0) - columns= 1; - - items= rows*columns; - - box= uiLayoutBox(layout); - row= uiLayoutRow(box, 0); - col = uiLayoutColumn(row, 1); - - uiBlockSetEmboss(block, UI_EMBOSSN); - - len= RNA_property_collection_length(ptr, prop); - scroll= MIN2(scroll, len-items+1); - scroll= MAX2(scroll, 1); - - RNA_PROP_BEGIN(ptr, itemptr, prop) { - if(i >= scroll && i<scroll+items) { - name= RNA_struct_name_get_alloc(&itemptr, NULL, 0); - - if(name) { -#if 0 - ListItem *item= MEM_callocN(sizeof(ListItem), "uiTemplateList ListItem"); - - item->ptr= *ptr; - item->prop= prop; - item->activeprop= activeprop; - item->activeptr= itemptr; - item->activei= i; - - if(activetype == PROP_POINTER) - item->selected= (activeptr.data == itemptr.data)? i: -1; - else if(activetype == PROP_INT) - item->selected= (activei == i)? i: -1; - else if(activetype == PROP_STRING) - item->selected= (strcmp(activename, name) == 0)? i: -1; -#endif - - //but= uiDefIconTextButI(block, ROW, 0, RNA_struct_ui_icon(itemptr.type), name, 0,0,UI_UNIT_X*10,UI_UNIT_Y, &item->selected, 0, i, 0, 0, ""); - but= uiDefIconTextButR(block, ROW, 0, RNA_struct_ui_icon(itemptr.type), name, 0,0,UI_UNIT_X*10,UI_UNIT_Y, ptr, activepropname, 0/*&item->selected*/, 0, i, 0, 0, ""); - uiButSetFlag(but, UI_ICON_LEFT|UI_TEXT_LEFT); - //uiButSetNFunc(but, list_item_cb, item, NULL); - - MEM_freeN(name); - - link= MEM_callocN(sizeof(CollectionPointerLink), "uiTemplateList return"); - link->ptr= itemptr; - BLI_addtail(&lb, link); - } - } - - i++; - } - RNA_PROP_END; - - while(i < scroll+items) { - if(i >= scroll) - uiItemL(col, "", 0); - i++; - } - - uiBlockSetEmboss(block, UI_EMBOSS); - - if(len > items) { - col= uiLayoutColumn(row, 0); - uiDefButI(block, SCROLL, 0, "", 0,0,UI_UNIT_X*0.75,UI_UNIT_Y*items, &scroll, 1, len-items+1, items, 0, ""); - } - - //uiDefButI(block, SCROLL, 0, "", 0,0,UI_UNIT_X*15,UI_UNIT_Y*0.75, &scroll, 1, 16-5, 5, 0, ""); - } - - return lb; -} - diff --git a/source/blender/editors/interface/interface_utils.c b/source/blender/editors/interface/interface_utils.c index eb79848d7d2..a75a3402774 100644 --- a/source/blender/editors/interface/interface_utils.c +++ b/source/blender/editors/interface/interface_utils.c @@ -43,7 +43,6 @@ #include "BKE_colortools.h" #include "BKE_context.h" #include "BKE_idprop.h" -#include "BKE_icons.h" #include "BKE_library.h" #include "BKE_main.h" #include "BKE_texture.h" @@ -111,12 +110,7 @@ uiBut *uiDefAutoButR(uiBlock *block, PointerRNA *ptr, PropertyRNA *prop, int ind but= uiDefButR(block, MENU, 0, NULL, x1, y1, x2, y2, ptr, propname, index, 0, 0, -1, -1, NULL); break; case PROP_STRING: - if(icon && name && strcmp(name, "") == 0) - but= uiDefIconButR(block, TEX, 0, icon, x1, y1, x2, y2, ptr, propname, index, 0, 0, -1, -1, NULL); - else if(icon) - but= uiDefIconTextButR(block, TEX, 0, icon, name, x1, y1, x2, y2, ptr, propname, index, 0, 0, -1, -1, NULL); - else - but= uiDefButR(block, TEX, 0, name, x1, y1, x2, y2, ptr, propname, index, 0, 0, -1, -1, NULL); + but= uiDefButR(block, TEX, 0, name, x1, y1, x2, y2, ptr, propname, index, 0, 0, -1, -1, NULL); break; case PROP_POINTER: { PointerRNA pptr; @@ -126,8 +120,6 @@ uiBut *uiDefAutoButR(uiBlock *block, PointerRNA *ptr, PropertyRNA *prop, int ind if(!pptr.type) pptr.type= RNA_property_pointer_type(ptr, prop); icon= RNA_struct_ui_icon(pptr.type); - if(icon == ICON_DOT) - icon= 0; but= uiDefIconTextButR(block, IDPOIN, 0, icon, name, x1, y1, x2, y2, ptr, propname, index, 0, 0, -1, -1, NULL); break; @@ -147,39 +139,69 @@ uiBut *uiDefAutoButR(uiBlock *block, PointerRNA *ptr, PropertyRNA *prop, int ind return but; } -void uiDefAutoButsRNA(const bContext *C, uiLayout *layout, PointerRNA *ptr, int columns) +void uiDefAutoButsRNA(const bContext *C, uiLayout *layout, PointerRNA *ptr) { - uiLayout *split, *col; + CollectionPropertyIterator iter; + PropertyRNA *iterprop, *prop; + uiLayout *split; char *name; uiItemL(layout, (char*)RNA_struct_ui_name(ptr->type), 0); - RNA_STRUCT_BEGIN(ptr, prop) { + iterprop= RNA_struct_iterator_property(ptr->type); + RNA_property_collection_begin(ptr, iterprop, &iter); + + for(; iter.valid; RNA_property_collection_next(&iter)) { + prop= iter.ptr.data; + if(strcmp(RNA_property_identifier(prop), "rna_type") == 0) continue; + split = uiLayoutSplit(layout, 0.5f); + name= (char*)RNA_property_ui_name(prop); - if(columns == 1) { - col= uiLayoutColumn(layout, 1); - uiItemL(col, name, 0); - } - else if(columns == 2) { - split = uiLayoutSplit(layout, 0.5f); + uiItemL(uiLayoutColumn(split, 0), name, 0); + uiItemFullR(uiLayoutColumn(split, 0), "", 0, ptr, prop, -1, 0, 0, 0, 0); + } - uiItemL(uiLayoutColumn(split, 0), name, 0); - col= uiLayoutColumn(split, 0); - } + RNA_property_collection_end(&iter); +} +/* temp call, single collumn, test for toolbar only */ +void uiDefAutoButsRNA_single(const bContext *C, uiLayout *layout, PointerRNA *ptr) +{ + CollectionPropertyIterator iter; + PropertyRNA *iterprop, *prop; + uiLayout *col; + char *name; + + uiItemL(layout, (char*)RNA_struct_ui_name(ptr->type), 0); + + iterprop= RNA_struct_iterator_property(ptr->type); + RNA_property_collection_begin(ptr, iterprop, &iter); + + for(; iter.valid; RNA_property_collection_next(&iter)) { + prop= iter.ptr.data; + + if(strcmp(RNA_property_identifier(prop), "rna_type") == 0) + continue; + + name= (char*)RNA_property_ui_name(prop); + col= uiLayoutColumn(layout, 1); + uiItemL(col, name, 0); + /* temp hack to show normal button for spin/screw */ if(strcmp(name, "Axis")==0) { - uiDefButR(uiLayoutGetBlock(col), BUT_NORMAL, 0, name, 0, 0, 100, 100, ptr, "axis", -1, 0, 0, -1, -1, NULL); + uiDefButR(uiLayoutGetBlock(layout), BUT_NORMAL, 0, name, 0, 0, 100, 100, ptr, "axis", -1, 0, 0, -1, -1, NULL); } else uiItemFullR(col, "", 0, ptr, prop, -1, 0, 0, 0, 0); } - RNA_STRUCT_END; + + RNA_property_collection_end(&iter); } + /***************************** ID Utilities *******************************/ /* note, C code version, will be replaced with version in interface_templates.c */ @@ -282,25 +304,9 @@ static void id_search_cb(const struct bContext *C, void *arg_params, char *str, ID *id; for(id= params->lb->first; id; id= id->next) { - int iconid= 0; - - - /* icon */ - switch(GS(id->name)) - { - case ID_MA: /* fall through */ - case ID_TE: /* fall through */ - case ID_IM: /* fall through */ - case ID_WO: /* fall through */ - case ID_LA: /* fall through */ - iconid= BKE_icon_getid(id); - break; - default: - break; - } if(BLI_strcasestr(id->name+2, str)) { - if(0==uiSearchItemAdd(items, id->name+2, id, iconid)) + if(0==uiSearchItemAdd(items, id->name+2, id)) break; } } @@ -327,7 +333,7 @@ static uiBlock *id_search_menu(bContext *C, ARegion *ar, void *arg_params) uiDefBut(block, LABEL, 0, "", 10, 15, 150, uiSearchBoxhHeight(), NULL, 0, 0, 0, 0, NULL); but= uiDefSearchBut(block, search, 0, ICON_VIEWZOOM, 256, 10, 0, 150, 19, ""); - uiButSetSearchFunc(but, id_search_cb, ¶ms, id_search_call_cb, NULL); + uiButSetSearchFunc(but, id_search_cb, ¶ms, id_search_call_cb); uiBoundsBlock(block, 6); uiBlockSetDirection(block, UI_DOWN); diff --git a/source/blender/editors/interface/interface_widgets.c b/source/blender/editors/interface/interface_widgets.c index ddf31c0db66..14df9026078 100644 --- a/source/blender/editors/interface/interface_widgets.c +++ b/source/blender/editors/interface/interface_widgets.c @@ -102,7 +102,6 @@ typedef struct uiWidgetBase { float inner_uv[64][2]; short inner, outline, emboss; /* set on/off */ - short shadedir; uiWidgetTrias tria1; uiWidgetTrias tria2; @@ -200,7 +199,6 @@ static void widget_init(uiWidgetBase *wtb) wtb->inner= 1; wtb->outline= 1; wtb->emboss= 1; - wtb->shadedir= 1; } /* helper call, makes shadow rect, with 'sun' above menu, so only shadow to left/right/bottom */ @@ -585,7 +583,7 @@ static void widgetbase_draw(uiWidgetBase *wtb, uiWidgetColors *wcol) glShadeModel(GL_SMOOTH); glBegin(GL_POLYGON); for(a=0; a<wtb->totvert; a++) { - round_box_shade_col4(col1, col2, wtb->inner_uv[a][wtb->shadedir]); + round_box_shade_col4(col1, col2, wtb->inner_uv[a][1]); glVertex2fv(wtb->inner_v[a]); } glEnd(); @@ -1028,7 +1026,7 @@ static struct uiWidgetColors wcol_menu_back= { {0, 0, 0, 255}, {25, 25, 25, 230}, {45, 45, 45, 230}, - {100, 100, 100, 255}, + {255, 255, 255, 255}, {255, 255, 255, 255}, {255, 255, 255, 255}, @@ -1090,32 +1088,6 @@ static struct uiWidgetColors wcol_box= { 0, 0 }; -static struct uiWidgetColors wcol_toggle= { - {25, 25, 25, 255}, - {153, 153, 153, 255}, - {100, 100, 100, 255}, - {25, 25, 25, 255}, - - {0, 0, 0, 255}, - {255, 255, 255, 255}, - - 0, - 0, 0 -}; - -static struct uiWidgetColors wcol_scroll= { - {25, 25, 25, 255}, - {180, 180, 180, 255}, - {153, 153, 153, 255}, - {90, 90, 90, 255}, - - {0, 0, 0, 255}, - {255, 255, 255, 255}, - - 1, - 0, -20 -}; - /* free wcol struct to play with */ static struct uiWidgetColors wcol_tmp= { {0, 0, 0, 255}, @@ -1137,10 +1109,9 @@ void ui_widget_color_init(ThemeUI *tui) tui->wcol_regular= wcol_regular; tui->wcol_tool= wcol_tool; - tui->wcol_text= wcol_text; tui->wcol_radio= wcol_radio; + tui->wcol_text= wcol_text; tui->wcol_option= wcol_option; - tui->wcol_toggle= wcol_toggle; tui->wcol_num= wcol_num; tui->wcol_numslider= wcol_numslider; tui->wcol_menu= wcol_menu; @@ -1148,7 +1119,6 @@ void ui_widget_color_init(ThemeUI *tui) tui->wcol_menu_back= wcol_menu_back; tui->wcol_menu_item= wcol_menu_item; tui->wcol_box= wcol_box; - tui->wcol_scroll= wcol_scroll; } /* ************ button callbacks, state ***************** */ @@ -1632,75 +1602,6 @@ void ui_draw_link_bezier(rcti *rect) } } -static void widget_scroll(uiBut *but, uiWidgetColors *wcol, rcti *rect, int state, int roundboxalign) -{ - uiWidgetBase wtb; - rcti rect1; - double value; - char inner[3]; - float fac, size, rad; - int horizontal; - - /* determine horizontal/vertical */ - horizontal= (rect->xmax - rect->xmin > rect->ymax - rect->ymin); - - if(horizontal) - rad= 0.5f*(rect->ymax - rect->ymin); - else - rad= 0.5f*(rect->xmax - rect->xmin); - - widget_init(&wtb); - wtb.shadedir= (horizontal)? 1: 0; - - /* draw back part, colors swapped and shading inverted */ - VECCOPY(inner, wcol->inner); - VECCOPY(wcol->inner, wcol->item); - if(horizontal) - SWAP(short, wcol->shadetop, wcol->shadedown); - if(state & UI_SELECT) - SWAP(short, wcol->shadetop, wcol->shadedown); - - round_box_edges(&wtb, roundboxalign, rect, rad); /* XXX vertical gradient is wrong */ - widgetbase_draw(&wtb, wcol); - - VECCOPY(wcol->inner, inner); - if(horizontal) - SWAP(short, wcol->shadetop, wcol->shadedown); - if(state & UI_SELECT) - SWAP(short, wcol->shadetop, wcol->shadedown); - - /* front part */ - value= ui_get_but_val(but); - - size= (but->softmax + but->a1 - but->softmin); - size= MAX2(size, 2); - - /* position */ - rect1= *rect; - - if(horizontal) { - fac= (rect->xmax - rect->xmin)/(size-1); - rect1.xmin= rect1.xmin + ceil(fac*(value - but->softmin)); - rect1.xmax= rect1.xmin + ceil(fac*(but->a1 - but->softmin)); - } - else { - fac= (rect->ymax - rect->ymin)/(size-1); - rect1.ymax= rect1.ymax - ceil(fac*(value - but->softmin)); - rect1.ymin= rect1.ymax - ceil(fac*(but->a1 - but->softmin)); - } - - /* draw */ - wtb.emboss= 0; /* only emboss once */ - - if(!horizontal) - SWAP(short, wcol->shadetop, wcol->shadedown); - - round_box_edges(&wtb, roundboxalign, &rect1, rad); /* XXX vertical gradient is wrong */ - widgetbase_draw(&wtb, wcol); - - if(!horizontal) - SWAP(short, wcol->shadetop, wcol->shadedown); -} static void widget_link(uiBut *but, uiWidgetColors *wcol, rcti *rect, int state, int roundboxalign) { @@ -1995,16 +1896,12 @@ static uiWidgetType *widget_type(uiWidgetTypeEnum type) wt.text= widget_draw_text_icon; switch(type) { - case UI_WTYPE_REGULAR: - break; - case UI_WTYPE_LABEL: wt.draw= NULL; wt.state= widget_state_label; break; case UI_WTYPE_TOGGLE: - wt.wcol_theme= &btheme->tui.wcol_toggle; break; case UI_WTYPE_OPTION: @@ -2017,7 +1914,7 @@ static uiWidgetType *widget_type(uiWidgetTypeEnum type) wt.wcol_theme= &btheme->tui.wcol_radio; wt.draw= widget_radiobut; break; - + case UI_WTYPE_NUMBER: wt.wcol_theme= &btheme->tui.wcol_num; wt.draw= widget_numbut; @@ -2098,11 +1995,6 @@ static uiWidgetType *widget_type(uiWidgetTypeEnum type) case UI_WTYPE_NORMAL: break; - - case UI_WTYPE_SCROLL: - wt.wcol_theme= &btheme->tui.wcol_scroll; - wt.custom= widget_scroll; - break; } return &wt; @@ -2197,7 +2089,6 @@ void ui_draw_but(const bContext *C, ARegion *ar, uiStyle *style, uiBut *but, rct case BUT: wt= widget_type(UI_WTYPE_EXEC); break; - case NUM: wt= widget_type(UI_WTYPE_NUMBER); break; @@ -2293,13 +2184,9 @@ void ui_draw_but(const bContext *C, ARegion *ar, uiStyle *style, uiBut *but, rct case BUT_CURVE: ui_draw_but_CURVE(ar, but, &tui->wcol_regular, rect); break; - - case SCROLL: - wt= widget_type(UI_WTYPE_SCROLL); - break; - + default: - wt= widget_type(UI_WTYPE_REGULAR); + wt= widget_type(UI_WTYPE_TOGGLE); } } @@ -2308,7 +2195,6 @@ void ui_draw_but(const bContext *C, ARegion *ar, uiStyle *style, uiBut *but, rct int roundboxalign, state; roundboxalign= widget_roundbox_set(but, rect); - state= but->flag; if(but->editstr) state |= UI_TEXTINPUT; @@ -2356,7 +2242,7 @@ void ui_draw_search_back(uiStyle *style, uiBlock *block, rcti *rect) /* helper call to draw a menu item without button */ /* state: UI_ACTIVE or 0 */ -void ui_draw_menu_item(uiFontStyle *fstyle, rcti *rect, char *name, int iconid, int state) +void ui_draw_menu_item(uiFontStyle *fstyle, rcti *rect, char *name, int state) { uiWidgetType *wt= widget_type(UI_WTYPE_MENU_ITEM); rcti _rect= *rect; @@ -2370,7 +2256,6 @@ void ui_draw_menu_item(uiFontStyle *fstyle, rcti *rect, char *name, int iconid, /* text location offset */ rect->xmin+=5; - if(iconid) rect->xmin+= ICON_HEIGHT; /* cut string in 2 parts? */ cpoin= strchr(name, '|'); @@ -2393,12 +2278,5 @@ void ui_draw_menu_item(uiFontStyle *fstyle, rcti *rect, char *name, int iconid, /* restore rect, was messed with */ *rect= _rect; - if(iconid) { - int xs= rect->xmin+4; - int ys= 1 + (rect->ymin+rect->ymax- ICON_HEIGHT)/2; - glEnable(GL_BLEND); - UI_icon_draw_aspect_blended(xs, ys, iconid, 1.2f, 0); /* XXX scale weak get from fstyle? */ - glDisable(GL_BLEND); - } } diff --git a/source/blender/editors/interface/resources.c b/source/blender/editors/interface/resources.c index f83dee23417..0a65718b708 100644 --- a/source/blender/editors/interface/resources.c +++ b/source/blender/editors/interface/resources.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: resources.c 12755 2007-12-02 05:50:38Z aligorith $ * * ***** BEGIN GPL/BL DUAL LICENSE BLOCK ***** * diff --git a/source/blender/editors/interface/view2d.c b/source/blender/editors/interface/view2d.c index aa5aa65d300..189898cc907 100644 --- a/source/blender/editors/interface/view2d.c +++ b/source/blender/editors/interface/view2d.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: view2d.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -316,12 +316,6 @@ void UI_view2d_curRect_validate(View2D *v2d) if (v2d->keepzoom & V2D_LOCKZOOM_Y) height= winy; - /* values used to divide, so make it safe */ - if(width<1) width= 1; - if(height<1) height= 1; - if(winx<1) winx= 1; - if(winy<1) winy= 1; - /* keepzoom (V2D_KEEPZOOM set), indicates that zoom level on each axis must not exceed limits * NOTE: in general, it is not expected that the lock-zoom will be used in conjunction with this */ diff --git a/source/blender/editors/mesh/Makefile b/source/blender/editors/mesh/Makefile index 8ae40e1b957..650771519cd 100644 --- a/source/blender/editors/mesh/Makefile +++ b/source/blender/editors/mesh/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/mesh/editmesh.c b/source/blender/editors/mesh/editmesh.c index 7f5201f4704..dd003d103d5 100644 --- a/source/blender/editors/mesh/editmesh.c +++ b/source/blender/editors/mesh/editmesh.c @@ -841,7 +841,7 @@ void make_editMesh(Scene *scene, Object *ob) em= me->edit_mesh; - em->selectmode= scene->toolsettings->selectmode; // warning needs to be synced + em->selectmode= scene->selectmode; // warning needs to be synced em->act_face = NULL; em->totvert= tot= me->totvert; em->totedge= me->totedge; @@ -1556,7 +1556,7 @@ static int mesh_separate_material(Scene *scene, Base *editbase) /* clear selection, we're going to use that to select material group */ EM_clear_flag_all(em, SELECT); /* select the material */ - EM_select_by_material(em, curr_mat); + editmesh_select_by_material(em, curr_mat); /* and now separate */ if(0==mesh_separate_selected(scene, editbase)) { BKE_mesh_end_editmesh(me, em); diff --git a/source/blender/editors/mesh/editmesh_add.c b/source/blender/editors/mesh/editmesh_add.c index 12138ee13d2..57fb2c19c75 100644 --- a/source/blender/editors/mesh/editmesh_add.c +++ b/source/blender/editors/mesh/editmesh_add.c @@ -1276,7 +1276,7 @@ static float new_primitive_matrix(bContext *C, float primmat[][4]) Object *obedit= CTX_data_edit_object(C); Scene *scene = CTX_data_scene(C); View3D *v3d =CTX_wm_view3d(C); - RegionView3D *rv3d= ED_view3d_context_rv3d(C); + RegionView3D *rv3d= CTX_wm_region_view3d(C); float *curs, mat[3][3], vmat[3][3], cmat[3][3], imat[3][3]; Mat4One(primmat); @@ -1295,9 +1295,9 @@ static float new_primitive_matrix(bContext *C, float primmat[][4]) /* center */ curs= give_cursor(scene, v3d); VECCOPY(primmat[3], curs); - VECSUB(primmat[3], primmat[3], obedit->obmat[3]); Mat3Inv(imat, mat); Mat3MulVecfl(imat, primmat[3]); + VECSUB(primmat[3], primmat[3], obedit->obmat[3]); if(v3d) return v3d->grid; return 1.0f; diff --git a/source/blender/editors/mesh/editmesh_mods.c b/source/blender/editors/mesh/editmesh_mods.c index 70a0c6b82da..a1f8b3251c8 100644 --- a/source/blender/editors/mesh/editmesh_mods.c +++ b/source/blender/editors/mesh/editmesh_mods.c @@ -3242,7 +3242,7 @@ static int toggle_select_all_exec(bContext *C, wmOperator *op) void MESH_OT_select_all_toggle(wmOperatorType *ot) { /* identifiers */ - ot->name= "Select/Deselect All"; + ot->name= "Select or Deselect All"; ot->idname= "MESH_OT_select_all_toggle"; /* api callbacks */ @@ -3484,7 +3484,7 @@ void MESH_OT_select_random(wmOperatorType *ot) RNA_def_float_percentage(ot->srna, "percent", 0.5f, 0.0f, 1.0f, "Percent", "Percentage of vertices to select randomly.", 0.0001f, 1.0f); } -void EM_select_by_material(EditMesh *em, int index) +void editmesh_select_by_material(EditMesh *em, int index) { EditFace *efa; @@ -3497,7 +3497,7 @@ void EM_select_by_material(EditMesh *em, int index) EM_selectmode_flush(em); } -void EM_deselect_by_material(EditMesh *em, int index) +void editmesh_deselect_by_material(EditMesh *em, int index) { EditFace *efa; @@ -3531,7 +3531,7 @@ static void mesh_selection_type(Scene *scene, EditMesh *em, int val) /* note, em stores selectmode to be able to pass it on everywhere without scene, this is only until all select modes and toolsettings are settled more */ - scene->toolsettings->selectmode= em->selectmode; + scene->selectmode= em->selectmode; // if (EM_texFaceCheck()) } } diff --git a/source/blender/editors/mesh/editmesh_tools.c b/source/blender/editors/mesh/editmesh_tools.c index dc9c8c6b6d2..b26fded4fb6 100644 --- a/source/blender/editors/mesh/editmesh_tools.c +++ b/source/blender/editors/mesh/editmesh_tools.c @@ -787,7 +787,7 @@ static int extrude_repeat_mesh(bContext *C, wmOperator *op) Object *obedit= CTX_data_edit_object(C); EditMesh *em= BKE_mesh_get_editmesh((Mesh *)obedit->data); - RegionView3D *rv3d = ED_view3d_context_rv3d(C); + RegionView3D *rv3d = CTX_wm_region_view3d(C); int steps = RNA_int_get(op->ptr,"steps"); @@ -949,7 +949,7 @@ static int spin_mesh_invoke(bContext *C, wmOperator *op, wmEvent *event) { Scene *scene = CTX_data_scene(C); View3D *v3d = CTX_wm_view3d(C); - RegionView3D *rv3d= ED_view3d_context_rv3d(C); + RegionView3D *rv3d= CTX_wm_region_view3d(C); RNA_float_set_array(op->ptr, "center", give_cursor(scene, v3d)); RNA_float_set_array(op->ptr, "axis", rv3d->viewinv[2]); @@ -1056,7 +1056,7 @@ static int screw_mesh_invoke(bContext *C, wmOperator *op, wmEvent *event) { Scene *scene = CTX_data_scene(C); View3D *v3d = CTX_wm_view3d(C); - RegionView3D *rv3d= ED_view3d_context_rv3d(C); + RegionView3D *rv3d= CTX_wm_region_view3d(C); RNA_float_set_array(op->ptr, "center", give_cursor(scene, v3d)); RNA_float_set_array(op->ptr, "axis", rv3d->viewinv[1]); diff --git a/source/blender/editors/object/Makefile b/source/blender/editors/object/Makefile index 70ada46c80f..c0312023bfd 100644 --- a/source/blender/editors/object/Makefile +++ b/source/blender/editors/object/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/object/object_edit.c b/source/blender/editors/object/object_edit.c index c436ccdb328..74a1fc12631 100644 --- a/source/blender/editors/object/object_edit.c +++ b/source/blender/editors/object/object_edit.c @@ -340,7 +340,7 @@ static int object_add_mesh_exec(bContext *C, wmOperator *op) if(obedit==NULL || obedit->type!=OB_MESH) { object_add_type(C, OB_MESH); - ED_object_enter_editmode(C, EM_DO_UNDO); + ED_object_enter_editmode(C, 0); newob = 1; } else DAG_object_flush_update(CTX_data_scene(C), obedit, OB_RECALC_DATA); @@ -388,7 +388,7 @@ static int object_add_mesh_exec(bContext *C, wmOperator *op) void OBJECT_OT_mesh_add(wmOperatorType *ot) { /* identifiers */ - ot->name= "Add Mesh"; + ot->name= "Mesh"; ot->description = "Add a mesh object to the scene."; ot->idname= "OBJECT_OT_mesh_add"; @@ -398,8 +398,8 @@ void OBJECT_OT_mesh_add(wmOperatorType *ot) ot->poll= ED_operator_scene_editable; - /* flags: no register or undo, this operator calls operators */ - ot->flag= 0; //OPTYPE_REGISTER|OPTYPE_UNDO; + /* flags */ + ot->flag= 0; RNA_def_enum(ot->srna, "type", prop_mesh_types, 0, "Primitive", ""); } @@ -462,7 +462,7 @@ static int object_add_curve_invoke(bContext *C, wmOperator *op, wmEvent *event) void OBJECT_OT_curve_add(wmOperatorType *ot) { /* identifiers */ - ot->name= "Add Curve"; + ot->name= "Curve"; ot->description = "Add a curve object to the scene."; ot->idname= "OBJECT_OT_curve_add"; @@ -520,7 +520,7 @@ static int object_add_surface_exec(bContext *C, wmOperator *op) void OBJECT_OT_surface_add(wmOperatorType *ot) { /* identifiers */ - ot->name= "Add Surface"; + ot->name= "Surface"; ot->description = "Add a surface object to the scene."; ot->idname= "OBJECT_OT_surface_add"; @@ -557,7 +557,7 @@ static int object_add_text_exec(bContext *C, wmOperator *op) void OBJECT_OT_text_add(wmOperatorType *ot) { /* identifiers */ - ot->name= "Add Text"; + ot->name= "Text"; ot->description = "Add a text object to the scene"; ot->idname= "OBJECT_OT_text_add"; @@ -602,7 +602,7 @@ static int object_armature_add_exec(bContext *C, wmOperator *op) void OBJECT_OT_armature_add(wmOperatorType *ot) { /* identifiers */ - ot->name= "Add Armature"; + ot->name= "Armature"; ot->description = "Add an armature object to the scene."; ot->idname= "OBJECT_OT_armature_add"; @@ -1395,8 +1395,7 @@ static int parent_clear_exec(bContext *C, wmOperator *op) DAG_scene_sort(CTX_data_scene(C)); ED_anim_dag_flush_update(C); - WM_event_add_notifier(C, NC_OBJECT|ND_TRANSFORM, NULL); - + return OPERATOR_FINISHED; } @@ -2601,8 +2600,7 @@ static int parent_set_exec(bContext *C, wmOperator *op) CTX_DATA_END; DAG_scene_sort(CTX_data_scene(C)); - ED_anim_dag_flush_update(C); - WM_event_add_notifier(C, NC_OBJECT|ND_TRANSFORM, NULL); + ED_anim_dag_flush_update(C); return OPERATOR_FINISHED; } @@ -2650,7 +2648,7 @@ void OBJECT_OT_parent_set(wmOperatorType *ot) ot->poll= ED_operator_object_active; /* flags */ - ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + ot->flag= 0; RNA_def_enum(ot->srna, "type", prop_make_parent_types, 0, "Type", ""); } @@ -3351,7 +3349,6 @@ void ED_object_enter_editmode(bContext *C, int flag) WM_event_add_notifier(C, NC_SCENE|ND_MODE|NS_MODE_OBJECT, scene); } - if(flag & EM_DO_UNDO) ED_undo_push(C, "Enter Editmode"); if(flag & EM_WAITCURSOR) waitcursor(0); } @@ -3664,7 +3661,7 @@ void special_editmenu(Scene *scene, View3D *v3d) if(!psys) return; - if(pset->selectmode & SCE_SELECT_POINT) + if(scene->selectmode & SCE_SELECT_POINT) nr= pupmenu("Specials%t|Rekey%x1|Subdivide%x2|Select First%x3|Select Last%x4|Remove Doubles%x5"); else nr= pupmenu("Specials%t|Rekey%x1|Remove Doubles%x5"); diff --git a/source/blender/editors/object/object_modifier.c b/source/blender/editors/object/object_modifier.c index 4bcfcc4d5ab..ee506220b67 100644 --- a/source/blender/editors/object/object_modifier.c +++ b/source/blender/editors/object/object_modifier.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: object_modifier.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/physics/Makefile b/source/blender/editors/physics/Makefile index 63968fdd537..a71ea9e2083 100644 --- a/source/blender/editors/physics/Makefile +++ b/source/blender/editors/physics/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/physics/editparticle.c b/source/blender/editors/physics/editparticle.c index 1b6b5b43522..b6625cb387c 100644 --- a/source/blender/editors/physics/editparticle.c +++ b/source/blender/editors/physics/editparticle.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: editparticle.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -225,7 +225,7 @@ void PE_hide_keys_time(Scene *scene, ParticleSystem *psys, float cfra) ParticleEditSettings *pset=PE_settings(scene); int i, k, totpart= psys->totpart; - if(pset->draw_timed && pset->selectmode==SCE_SELECT_POINT) { + if(pset->draw_timed && scene->selectmode==SCE_SELECT_POINT) { LOOP_PARTICLES(i, pa) { LOOP_KEYS(k, key) { if(fabs(cfra-*key->time) < pset->draw_timed) @@ -425,12 +425,11 @@ static void for_mouse_hit_keys(PEData *data, ForKeyFunc func, int nearest) ParticleEdit *edit= psys->edit; ParticleData *pa; ParticleEditKey *key; - ParticleEditSettings *pset= PE_settings(data->scene); int i, k, totpart, nearest_pa, nearest_key; float dist= data->rad; /* in path select mode we have no keys */ - if(pset->selectmode==SCE_SELECT_PATH) + if(data->scene->selectmode==SCE_SELECT_PATH) return; totpart= psys->totpart; @@ -440,7 +439,7 @@ static void for_mouse_hit_keys(PEData *data, ForKeyFunc func, int nearest) LOOP_PARTICLES(i, pa) { if(pa->flag & PARS_HIDE) continue; - if(pset->selectmode == SCE_SELECT_END) { + if(data->scene->selectmode == SCE_SELECT_END) { /* only do end keys */ key= edit->keys[i] + pa->totkey-1; @@ -482,19 +481,18 @@ static void foreach_mouse_hit_particle(PEData *data, ForParticleFunc func, int s ParticleSystem *psys= data->psys; ParticleData *pa; ParticleEditKey *key; - ParticleEditSettings *pset= PE_settings(data->scene); int i, k, totpart; totpart= psys->totpart; /* all is selected in path mode */ - if(pset->selectmode==SCE_SELECT_PATH) + if(data->scene->selectmode==SCE_SELECT_PATH) selected=0; LOOP_PARTICLES(i, pa) { if(pa->flag & PARS_HIDE) continue; - if(pset->selectmode==SCE_SELECT_END) { + if(data->scene->selectmode==SCE_SELECT_END) { /* only do end keys */ key= psys->edit->keys[i] + pa->totkey-1; @@ -524,7 +522,6 @@ static void foreach_mouse_hit_key(PEData *data, ForKeyMatFunc func, int selected ParticleData *pa; ParticleEditKey *key; ParticleSystemModifierData *psmd=0; - ParticleEditSettings *pset= PE_settings(data->scene); int i, k, totpart; float mat[4][4], imat[4][4]; @@ -532,7 +529,7 @@ static void foreach_mouse_hit_key(PEData *data, ForKeyMatFunc func, int selected totpart= psys->totpart; /* all is selected in path mode */ - if(pset->selectmode==SCE_SELECT_PATH) + if(data->scene->selectmode==SCE_SELECT_PATH) selected= 0; Mat4One(imat); @@ -544,7 +541,7 @@ static void foreach_mouse_hit_key(PEData *data, ForKeyMatFunc func, int selected psys_mat_hair_to_global(data->ob, psmd->dm, psys->part->from, pa, mat); Mat4Invert(imat,mat); - if(pset->selectmode==SCE_SELECT_END) { + if(data->scene->selectmode==SCE_SELECT_END) { /* only do end keys */ key= psys->edit->keys[i] + pa->totkey-1; @@ -613,7 +610,6 @@ static int count_selected_keys(Scene *scene, ParticleSystem *psys) { ParticleData *pa; ParticleEditKey *key; - ParticleEditSettings *pset= PE_settings(scene); int i, k, totpart, sel= 0; totpart= psys->totpart; @@ -623,12 +619,12 @@ static int count_selected_keys(Scene *scene, ParticleSystem *psys) key= psys->edit->keys[i]; - if(pset->selectmode==SCE_SELECT_POINT) { + if(scene->selectmode==SCE_SELECT_POINT) { for(k=0; k<pa->totkey; k++,key++) if(key->flag & PEK_SELECT) sel++; } - else if(pset->selectmode==SCE_SELECT_END) { + else if(scene->selectmode==SCE_SELECT_END) { key += pa->totkey-1; if(key->flag & PEK_SELECT) @@ -1458,7 +1454,6 @@ int PE_lasso_select(bContext *C, short mcords[][2], short moves, short select) ParticleEdit *edit; ParticleData *pa; ParticleEditKey *key; - ParticleEditSettings *pset= PE_settings(scene); float co[3], mat[4][4]; short vertco[2]; int i, k, totpart; @@ -1475,7 +1470,7 @@ int PE_lasso_select(bContext *C, short mcords[][2], short moves, short select) psys_mat_hair_to_global(ob, psmd->dm, psys->part->from, pa, mat); - if(pset->selectmode==SCE_SELECT_POINT) { + if(scene->selectmode==SCE_SELECT_POINT) { LOOP_KEYS(k, key) { VECCOPY(co, key->co); Mat4MulVecfl(mat, co); @@ -1492,7 +1487,7 @@ int PE_lasso_select(bContext *C, short mcords[][2], short moves, short select) } } } - else if(pset->selectmode==SCE_SELECT_END) { + else if(scene->selectmode==SCE_SELECT_END) { key= edit->keys[i] + pa->totkey - 1; VECCOPY(co, key->co); @@ -2354,7 +2349,7 @@ enum { DEL_PARTICLE, DEL_KEY }; static EnumPropertyItem delete_type_items[]= { {DEL_PARTICLE, "PARTICLE", 0, "Particle", ""}, {DEL_KEY, "KEY", 0, "Key", ""}, - {0, NULL, 0, NULL, NULL}}; + {0, NULL, NULL}}; static void set_delete_particle(PEData *data, int pa_index) { @@ -3847,7 +3842,6 @@ void PE_change_act_psys(Scene *scene, Object *ob, ParticleSystem *psys) static int specials_menu_invoke(bContext *C, wmOperator *op, wmEvent *event) { Scene *scene= CTX_data_scene(C); - ParticleEditSettings *pset=PE_settings(scene); uiPopupMenu *pup; uiLayout *layout; @@ -3855,7 +3849,7 @@ static int specials_menu_invoke(bContext *C, wmOperator *op, wmEvent *event) layout= uiPupMenuLayout(pup); uiItemO(layout, NULL, 0, "PARTICLE_OT_rekey"); - if(pset->selectmode & SCE_SELECT_POINT) { + if(scene->selectmode & SCE_SELECT_POINT) { uiItemO(layout, NULL, 0, "PARTICLE_OT_subdivide"); uiItemO(layout, NULL, 0, "PARTICLE_OT_select_first"); uiItemO(layout, NULL, 0, "PARTICLE_OT_select_last"); diff --git a/source/blender/editors/physics/physics_intern.h b/source/blender/editors/physics/physics_intern.h index e03649575cb..cbc94b3a058 100644 --- a/source/blender/editors/physics/physics_intern.h +++ b/source/blender/editors/physics/physics_intern.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: physics_intern.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/preview/Makefile b/source/blender/editors/preview/Makefile index 48e1dc64673..c44da6753f3 100644 --- a/source/blender/editors/preview/Makefile +++ b/source/blender/editors/preview/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/preview/previewrender.c b/source/blender/editors/preview/previewrender.c index 1efa5108b96..1ce20fcb0af 100644 --- a/source/blender/editors/preview/previewrender.c +++ b/source/blender/editors/preview/previewrender.c @@ -114,12 +114,46 @@ typedef struct ShaderPreview { ID *id; int sizex, sizey; - int *pr_rect; int pr_method; } ShaderPreview; +static void set_previewrect(ScrArea *sa, RenderInfo *ri) +{ + ARegion *ar= NULL; // XXX + rctf viewplane; + + BLI_init_rctf(&viewplane, PR_XMIN, PR_XMAX, PR_YMIN, PR_YMAX); + +// ui_graphics_to_window_rct(ar->win, &viewplane, &ri->disprect); + + /* correction for gla draw */ + BLI_translate_rcti(&ri->disprect, -ar->winrct.xmin, -ar->winrct.ymin); + + glMatrixMode(GL_PROJECTION); + glPushMatrix(); + glMatrixMode(GL_MODELVIEW); + glPushMatrix(); + + glaDefine2DArea(&ar->winrct); + + ri->pr_rectx= (ri->disprect.xmax-ri->disprect.xmin); + ri->pr_recty= (ri->disprect.ymax-ri->disprect.ymin); +} + +static void end_previewrect(ARegion *ar) +{ + glMatrixMode(GL_PROJECTION); + glPopMatrix(); + glMatrixMode(GL_MODELVIEW); + glPopMatrix(); + + // restore viewport / scissor which was set by glaDefine2DArea + glViewport(ar->winrct.xmin, ar->winrct.ymin, ar->winx, ar->winy); + glScissor(ar->winrct.xmin, ar->winrct.ymin, ar->winx, ar->winy); + +} /* unused now */ void draw_tex_crop(Tex *tex) @@ -404,6 +438,196 @@ static Scene *preview_prepare_scene(Scene *scene, int id_type, ShaderPreview *sp return NULL; } +void previewrender_progress(void *handle, RenderResult *rr, volatile rcti *renrect) +{ + SpaceButs *sbuts= NULL; // XXX + RenderLayer *rl; + RenderInfo *ri= sbuts->ri; + float ofsx, ofsy; + + if(renrect) return; + + rl= rr->layers.first; + + ofsx= ri->disprect.xmin + rr->tilerect.xmin; + ofsy= ri->disprect.ymin + rr->tilerect.ymin; + + glDrawBuffer(GL_FRONT); + glaDrawPixelsSafe_to32(ofsx, ofsy, rr->rectx, rr->recty, rr->rectx, rl->rectf); + bglFlush(); + glDrawBuffer(GL_BACK); +} + + +/* called by interface_icons.c, or by BIF_previewrender_buts or by nodes... */ +void BIF_previewrender(Scene *scene, struct ID *id, struct RenderInfo *ri, struct ScrArea *area, int pr_method) +{ + SpaceButs *sbuts= NULL; // XXX + Render *re; + RenderStats *rstats; + Scene *sce; + int oldx= ri->pr_rectx, oldy= ri->pr_recty; + char name [32]; + + if(ri->tottile && ri->curtile>=ri->tottile) return; + + /* check for return with a new event */ + if(pr_method!=PR_ICON_RENDER && qtest()) { +// if(area) +// addafterqueue(area->win, RENDERPREVIEW, 1); + return; + } + + /* get the stuff from the builtin preview dbase */ +// sce= preview_prepare_scene(scene, ri, GS(id->name), id, pr_method); + if(sce==NULL) return; + + /* set drawing conditions OK */ + if(area) { + sbuts= area->spacedata.first; /* needed for flag */ + + set_previewrect(area, ri); // uses UImat + + /* because preview render size can differs */ + if(ri->rect && (oldx!=ri->pr_rectx || oldy!=ri->pr_recty)) { + MEM_freeN(ri->rect); + ri->rect= NULL; + ri->curtile= 0; + } + } + +// XXX sprintf(name, "ButsPreview %d", area?area->win:0); + re= RE_GetRender(name); + + /* full refreshed render from first tile */ + if(re==NULL || ri->curtile==0) { + + re= RE_NewRender(name); + + /* handle cases */ + if(pr_method==PR_DRAW_RENDER) { +// RE_display_draw_cb(re, previewrender_progress); +// RE_test_break_cb(re, qtest); + sce->r.scemode |= R_NODE_PREVIEW; + if(sbuts->flag & SB_PRV_OSA) + sce->r.mode |= R_OSA; + sce->r.scemode &= ~R_NO_IMAGE_LOAD; + } + else if(pr_method==PR_DO_RENDER) { +// RE_test_break_cb(re, qtest); + sce->r.scemode |= R_NODE_PREVIEW; + sce->r.scemode &= ~R_NO_IMAGE_LOAD; + } + else { /* PR_ICON_RENDER */ + sce->r.scemode &= ~R_NODE_PREVIEW; + sce->r.scemode |= R_NO_IMAGE_LOAD; + } + + /* allocates render result */ + RE_InitState(re, NULL, &sce->r, ri->pr_rectx, ri->pr_recty, NULL); + + /* enforce preview image clear */ + if(GS(id->name)==ID_MA) { + Material *ma= (Material *)id; + ntreeClearPreview(ma->nodetree); + } + } + /* entire cycle for render engine */ + RE_SetCamera(re, sce->camera); + RE_Database_FromScene(re, sce, 1); + RE_TileProcessor(re, ri->curtile, 0); // actual render engine + RE_Database_Free(re); + + /* handle results */ + if(pr_method==PR_ICON_RENDER) { + if(ri->rect==NULL) + ri->rect= MEM_mallocN(sizeof(int)*ri->pr_rectx*ri->pr_recty, "BIF_previewrender"); + RE_ResultGet32(re, ri->rect); + } + else { + rstats= RE_GetStats(re); + + if(rstats->partsdone!=ri->curtile) { + if(ri->rect==NULL) + ri->rect= MEM_mallocN(sizeof(int)*ri->pr_rectx*ri->pr_recty, "BIF_previewrender"); + RE_ResultGet32(re, ri->rect); + } + + if(rstats->totpart==rstats->partsdone && rstats->partsdone) { + // allqueues + } + else { +// if(pr_method==PR_DRAW_RENDER && qtest()) +// addafterqueue(area->win, RENDERPREVIEW, 1); + } + + ri->curtile= rstats->partsdone; + ri->tottile= rstats->totpart; + } + + /* unassign the pointers, reset vars */ +// preview_prepare_scene(scene, ri, GS(id->name), NULL, 0); + +} + + +/* afterqueue call */ +void BIF_previewrender_buts(Scene *scene, SpaceButs *sbuts) +{ +// ScrArea *sa= NULL; // XXX + ARegion *ar= NULL; // XXX + uiBlock *block; + struct ID* id = 0; +// struct ID* idfrom = 0; + struct ID* idshow = 0; + Object *ob; + + if (!sbuts->ri) return; + + +// block= uiFindOpenPanelBlockName(&sa->uiblocks, "Preview"); + if(block==NULL) return; + + ob= ((scene->basact)? (scene->basact)->object: 0); + + /* we cant trust this global lockpoin.. for example with headerless window */ +// buttons_active_id(&id, &idfrom); + sbuts->lockpoin= id; + + if(sbuts->mainb==CONTEXT_SHADING) { + int tab= TAB_SHADING_MAT; // XXX sbuts->tab[CONTEXT_SHADING]; + + if(tab==TAB_SHADING_MAT) + idshow = sbuts->lockpoin; + else if(tab==TAB_SHADING_TEX) + idshow = sbuts->lockpoin; + else if(tab==TAB_SHADING_LAMP) { + if(ob && ob->type==OB_LAMP) idshow= ob->data; + } + else if(tab==TAB_SHADING_WORLD) + idshow = sbuts->lockpoin; + } + else if(sbuts->mainb==CONTEXT_OBJECT) { + if(ob && ob->type==OB_LAMP) idshow = ob->data; + } + + if (idshow) { + BKE_icon_changed(BKE_icon_getid(idshow)); +// uiPanelPush(block); +// BIF_previewrender(scene, idshow, sbuts->ri, sbuts->area, PR_DRAW_RENDER); +// uiPanelPop(block); + end_previewrect(ar); + } + else { + /* no active block to draw. But we do draw black if possible */ + if(sbuts->ri->rect) { + memset(sbuts->ri->rect, 0, sizeof(int)*sbuts->ri->pr_rectx*sbuts->ri->pr_recty); + sbuts->ri->tottile= 10000; +// addqueue(sa->win, REDRAW, 1); + } + return; + } +} /* new UI convention: draw is in pixel space already. */ /* uses ROUNDBOX button in block to get the rect */ @@ -782,7 +1006,7 @@ static void shader_preview_updatejob(void *spv) } -/* runs inside thread for material, in foreground for icons */ +/* runs inside thread */ static void shader_preview_startjob(void *customdata, short *stop, short *do_update) { ShaderPreview *sp= customdata; @@ -840,8 +1064,9 @@ static void shader_preview_startjob(void *customdata, short *stop, short *do_upd /* handle results */ if(sp->pr_method==PR_ICON_RENDER) { - if(sp->pr_rect) - RE_ResultGet32(re, sp->pr_rect); + //if(ri->rect==NULL) + // ri->rect= MEM_mallocN(sizeof(int)*ri->pr_rectx*ri->pr_recty, "BIF_previewrender"); + //RE_ResultGet32(re, ri->rect); } else { /* validate owner */ @@ -888,29 +1113,6 @@ void ED_preview_shader_job(const bContext *C, void *owner, ID *id, int sizex, in WM_jobs_callbacks(steve, shader_preview_startjob, NULL, shader_preview_updatejob); WM_jobs_start(CTX_wm_manager(C), steve); - - /* signal to rerender icon in menus */ - BKE_icon_changed(BKE_icon_getid(id)); } -/* rect should be allocated, sizex/sizy pixels, 32 bits */ -void ED_preview_iconrender(Scene *scene, ID *id, int *rect, int sizex, int sizey) -{ - ShaderPreview *sp= MEM_callocN(sizeof(ShaderPreview), "ShaderPreview"); - short stop=0, do_update=0; - - /* customdata for preview thread */ - sp->scene= scene; - sp->sizex= sizex; - sp->sizey= sizey; - sp->pr_method= PR_ICON_RENDER; - sp->pr_rect= rect; - sp->id = id; - - shader_preview_startjob(sp, &stop, &do_update); - - MEM_freeN(sp); -} - - diff --git a/source/blender/editors/screen/Makefile b/source/blender/editors/screen/Makefile index 923a020afcf..cf6e692c304 100644 --- a/source/blender/editors/screen/Makefile +++ b/source/blender/editors/screen/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/screen/area.c b/source/blender/editors/screen/area.c index 535e99ccfef..07d8fb370e6 100644 --- a/source/blender/editors/screen/area.c +++ b/source/blender/editors/screen/area.c @@ -259,16 +259,14 @@ static void region_scissor_winrct(ARegion *ar, rcti *winrct) while(ar->prev) { ar= ar->prev; - if(BLI_isect_rcti(winrct, &ar->winrct, NULL)) { - if(ar->flag & RGN_FLAG_HIDDEN); - else if(ar->alignment==RGN_OVERLAP_LEFT) { - winrct->xmin= ar->winrct.xmax + 1; - } - else if(ar->alignment==RGN_OVERLAP_RIGHT) { - winrct->xmax= ar->winrct.xmin - 1; - } - else break; + if(ar->flag & RGN_FLAG_HIDDEN); + else if(ar->alignment==RGN_OVERLAP_LEFT) { + winrct->xmin= ar->winrct.xmax + 1; + } + else if(ar->alignment==RGN_OVERLAP_RIGHT) { + winrct->xmax= ar->winrct.xmin - 1; } + else break; } } diff --git a/source/blender/editors/screen/glutil.c b/source/blender/editors/screen/glutil.c index a23487effa1..a81a52fd544 100644 --- a/source/blender/editors/screen/glutil.c +++ b/source/blender/editors/screen/glutil.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: glutil.c 11920 2007-09-02 17:25:03Z elubie $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/screen/screen_ops.c b/source/blender/editors/screen/screen_ops.c index dcfdfbf8285..2aa6758850e 100644 --- a/source/blender/editors/screen/screen_ops.c +++ b/source/blender/editors/screen/screen_ops.c @@ -59,7 +59,6 @@ #include "ED_util.h" #include "ED_screen.h" #include "ED_mesh.h" -#include "ED_object.h" #include "ED_screen_types.h" #include "RE_pipeline.h" @@ -2510,9 +2509,7 @@ static int screen_render_invoke(bContext *C, wmOperator *op, wmEvent *event) /* flush multires changes (for sculpt) */ multires_force_update(CTX_data_active_object(C)); - /* get editmode results */ - ED_object_exit_editmode(C, 0); /* 0 = does not exit editmode */ - + // get editmode results // store spare // get view3d layer, local layer, make this nice api call to render // store spare diff --git a/source/blender/editors/sculpt_paint/Makefile b/source/blender/editors/sculpt_paint/Makefile index 012a39b8d25..9353116a4bc 100644 --- a/source/blender/editors/sculpt_paint/Makefile +++ b/source/blender/editors/sculpt_paint/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/sculpt_paint/sculpt.c b/source/blender/editors/sculpt_paint/sculpt.c index 8f0b52ef3a1..fa33e214737 100644 --- a/source/blender/editors/sculpt_paint/sculpt.c +++ b/source/blender/editors/sculpt_paint/sculpt.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: sculptmode.c 18309 2009-01-04 07:47:11Z nicholasbishop $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -148,7 +148,6 @@ typedef struct StrokeCache { float *layer_disps; /* Displacements for each vertex */ float (*mesh_store)[3]; /* Copy of the mesh vertices' locations */ short (*orig_norms)[3]; /* Copy of the mesh vertices' normals */ - float (*face_norms)[3]; /* Copy of the mesh faces' normals */ float rotation; /* Texture rotation (radians) for anchored and rake modes */ int pixel_radius, previous_pixel_radius; ListBase grab_active_verts[8]; /* The same list of verts is used throught grab stroke */ @@ -241,6 +240,7 @@ static float brush_strength(Sculpt *sd, StrokeCache *cache) float dir= sd->brush->flag & BRUSH_DIR_IN ? -1 : 1; float pressure= 1; float flip= cache->flip ? -1:1; + float anchored = sd->brush->flag & BRUSH_ANCHORED ? 25 : 1; if(sd->brush->flag & BRUSH_ALPHA_PRESSURE) pressure *= cache->pressure; @@ -250,7 +250,6 @@ static float brush_strength(Sculpt *sd, StrokeCache *cache) case SCULPT_TOOL_INFLATE: case SCULPT_TOOL_CLAY: case SCULPT_TOOL_FLATTEN: - case SCULPT_TOOL_LAYER: return alpha * dir * pressure * flip; /*XXX: not sure why? was multiplied by G.vd->grid */; case SCULPT_TOOL_SMOOTH: return alpha * 4 * pressure; @@ -258,27 +257,46 @@ static float brush_strength(Sculpt *sd, StrokeCache *cache) return alpha / 2 * dir * pressure * flip; case SCULPT_TOOL_GRAB: return 1; + case SCULPT_TOOL_LAYER: + return sd->brush->alpha / 50.0f * dir * pressure * flip * anchored; /*XXX: not sure why? multiplied by G.vd->grid */; default: return 0; } } -/* Handles clipping against a mirror modifier and SCULPT_LOCK axis flags */ -static void sculpt_clip(Sculpt *sd, float *co, const float val[3]) +/* For clipping against a mirror modifier */ +static void sculpt_clip(StrokeCache *cache, float *co, const float val[3]) { int i; - for(i=0; i<3; ++i) { - if(sd->flags & (SCULPT_LOCK_X << i)) - continue; - - if((sd->session->cache->flag & (CLIP_X << i)) && (fabs(co[i]) <= sd->session->cache->clip_tolerance[i])) + if((cache->flag & (CLIP_X << i)) && (fabs(co[i]) <= cache->clip_tolerance[i])) co[i]= 0.0f; else co[i]= val[i]; } } +static void sculpt_axislock(Sculpt *sd, float *co) +{ + if(sd->flags == (SCULPT_LOCK_X|SCULPT_LOCK_Y|SCULPT_LOCK_Z)) + return; + + if(sd->session->cache->vc.v3d->twmode == V3D_MANIP_LOCAL) { + float mat[3][3], imat[3][3]; + Mat3CpyMat4(mat, sd->session->cache->vc.obact->obmat); + Mat3Inv(imat, mat); + Mat3MulVecfl(mat, co); + if (sd->flags & SCULPT_LOCK_X) co[0] = 0.0; + if (sd->flags & SCULPT_LOCK_Y) co[1] = 0.0; + if (sd->flags & SCULPT_LOCK_Z) co[2] = 0.0; + Mat3MulVecfl(imat, co); + } else { + if (sd->flags & SCULPT_LOCK_X) co[0] = 0.0; + if (sd->flags & SCULPT_LOCK_Y) co[1] = 0.0; + if (sd->flags & SCULPT_LOCK_Z) co[2] = 0.0; + } +} + static void add_norm_if(float view_vec[3], float out[3], float out_flip[3], const short no[3]) { float fno[3] = {no[0], no[1], no[2]}; @@ -335,6 +353,8 @@ static void do_draw_brush(Sculpt *sd, SculptSession *ss, const ListBase* active_ calc_area_normal(sd, area_normal, active_verts); + sculpt_axislock(sd, area_normal); + while(node){ float *co= ss->mvert[node->Index].co; @@ -342,7 +362,7 @@ static void do_draw_brush(Sculpt *sd, SculptSession *ss, const ListBase* active_ co[1]+area_normal[1]*ss->cache->radius*node->Fade*ss->cache->scale[1], co[2]+area_normal[2]*ss->cache->radius*node->Fade*ss->cache->scale[2]}; - sculpt_clip(sd, co, val); + sculpt_clip(ss->cache, co, val); node= node->next; } @@ -392,37 +412,37 @@ static void neighbor_average(SculptSession *ss, float avg[3], const int vert) VecCopyf(avg, ss->mvert[vert].co); } -static void do_smooth_brush(Sculpt *s, const ListBase* active_verts) +static void do_smooth_brush(SculptSession *ss, const ListBase* active_verts) { ActiveData *node= active_verts->first; int i; for(i = 0; i < 2; ++i) { while(node){ - float *co= s->session->mvert[node->Index].co; + float *co= ss->mvert[node->Index].co; float avg[3], val[3]; - neighbor_average(s->session, avg, node->Index); + neighbor_average(ss, avg, node->Index); val[0] = co[0]+(avg[0]-co[0])*node->Fade; val[1] = co[1]+(avg[1]-co[1])*node->Fade; val[2] = co[2]+(avg[2]-co[2])*node->Fade; - sculpt_clip(s, co, val); + sculpt_clip(ss->cache, co, val); node= node->next; } } } -static void do_pinch_brush(Sculpt *s, const ListBase* active_verts) +static void do_pinch_brush(SculptSession *ss, const ListBase* active_verts) { ActiveData *node= active_verts->first; while(node) { - float *co= s->session->mvert[node->Index].co; - const float val[3]= {co[0]+(s->session->cache->location[0]-co[0])*node->Fade, - co[1]+(s->session->cache->location[1]-co[1])*node->Fade, - co[2]+(s->session->cache->location[2]-co[2])*node->Fade}; - sculpt_clip(s, co, val); + float *co= ss->mvert[node->Index].co; + const float val[3]= {co[0]+(ss->cache->location[0]-co[0])*node->Fade, + co[1]+(ss->cache->location[1]-co[1])*node->Fade, + co[2]+(ss->cache->location[2]-co[2])*node->Fade}; + sculpt_clip(ss->cache, co, val); node= node->next; } } @@ -434,6 +454,7 @@ static void do_grab_brush(Sculpt *sd, SculptSession *ss) float grab_delta[3]; VecCopyf(grab_delta, ss->cache->grab_delta_symmetry); + sculpt_axislock(sd, grab_delta); while(node) { float *co= ss->mvert[node->Index].co; @@ -441,7 +462,7 @@ static void do_grab_brush(Sculpt *sd, SculptSession *ss) VecCopyf(add, grab_delta); VecMulf(add, node->Fade); VecAddf(add, add, co); - sculpt_clip(sd, co, add); + sculpt_clip(ss->cache, co, add); node= node->next; } @@ -452,38 +473,42 @@ static void do_layer_brush(Sculpt *sd, SculptSession *ss, const ListBase *active { float area_normal[3]; ActiveData *node= active_verts->first; - float lim= ss->cache->radius / 4; + float lim= brush_strength(sd, ss->cache); - if(ss->cache->flip) + if(sd->brush->flag & BRUSH_DIR_IN) lim = -lim; calc_area_normal(sd, area_normal, active_verts); while(node){ float *disp= &ss->cache->layer_disps[node->Index]; - float *co= ss->mvert[node->Index].co; - float val[3]; - - *disp+= node->Fade; - - /* Don't let the displacement go past the limit */ - if((lim < 0 && *disp < lim) || (lim > 0 && *disp > lim)) - *disp = lim; - val[0] = ss->cache->mesh_store[node->Index][0]+area_normal[0] * *disp*ss->cache->scale[0]; - val[1] = ss->cache->mesh_store[node->Index][1]+area_normal[1] * *disp*ss->cache->scale[1]; - val[2] = ss->cache->mesh_store[node->Index][2]+area_normal[2] * *disp*ss->cache->scale[2]; - - sculpt_clip(sd, co, val); + if((lim > 0 && *disp < lim) || + (lim < 0 && *disp > lim)) { + float *co= ss->mvert[node->Index].co; + float val[3]; + + *disp+= node->Fade; + + if(lim < 0 && *disp < lim) + *disp = lim; + else if(lim > 0 && *disp > lim) + *disp = lim; + + val[0] = ss->cache->mesh_store[node->Index][0]+area_normal[0] * *disp*ss->cache->scale[0]; + val[1] = ss->cache->mesh_store[node->Index][1]+area_normal[1] * *disp*ss->cache->scale[1]; + val[2] = ss->cache->mesh_store[node->Index][2]+area_normal[2] * *disp*ss->cache->scale[2]; + //VecMulf(val, ss->cache->radius); + sculpt_clip(ss->cache, co, val); + } node= node->next; } } -static void do_inflate_brush(Sculpt *s, const ListBase *active_verts) +static void do_inflate_brush(SculptSession *ss, const ListBase *active_verts) { ActiveData *node= active_verts->first; - SculptSession *ss = s->session; float add[3]; while(node) { @@ -499,7 +524,7 @@ static void do_inflate_brush(Sculpt *s, const ListBase *active_verts) add[2]*= ss->cache->scale[2]; VecAddf(add, add, co); - sculpt_clip(s, co, add); + sculpt_clip(ss->cache, co, add); node= node->next; } @@ -562,7 +587,7 @@ static void do_flatten_clay_brush(Sculpt *sd, SculptSession *ss, const ListBase VecAddf(val, val, tmp); } - sculpt_clip(sd, co, val); + sculpt_clip(ss->cache, co, val); node= node->next; } @@ -738,6 +763,37 @@ static void sculpt_add_damaged_rect(SculptSession *ss) } } +/* Clears the depth buffer in each modified area. */ +#if 0 +static void sculpt_clear_damaged_areas(SculptSession *ss) +{ + RectNode *rn= NULL; + + for(rn = ss->damaged_rects.first; rn; rn = rn->next) { + rcti clp = rn->r; + rcti *win = NULL; /*XXX: &curarea->winrct; */ + + clp.xmin += win->xmin; + clp.xmax += win->xmin; + clp.ymin += win->ymin; + clp.ymax += win->ymin; + + if(clp.xmin < win->xmax && clp.xmax > win->xmin && + clp.ymin < win->ymax && clp.ymax > win->ymin) { + if(clp.xmin < win->xmin) clp.xmin = win->xmin; + if(clp.ymin < win->ymin) clp.ymin = win->ymin; + if(clp.xmax > win->xmax) clp.xmax = win->xmax; + if(clp.ymax > win->ymax) clp.ymax = win->ymax; + + glScissor(clp.xmin + 1, clp.ymin + 1, + clp.xmax - clp.xmin - 2, + clp.ymax - clp.ymin - 2); + } + + glClear(GL_DEPTH_BUFFER_BIT); + } +} +#endif static void do_brush_action(Sculpt *sd, StrokeCache *cache) { SculptSession *ss = sd->session; @@ -789,13 +845,13 @@ static void do_brush_action(Sculpt *sd, StrokeCache *cache) do_draw_brush(sd, ss, &active_verts); break; case SCULPT_TOOL_SMOOTH: - do_smooth_brush(sd, &active_verts); + do_smooth_brush(ss, &active_verts); break; case SCULPT_TOOL_PINCH: - do_pinch_brush(sd, &active_verts); + do_pinch_brush(ss, &active_verts); break; case SCULPT_TOOL_INFLATE: - do_inflate_brush(sd, &active_verts); + do_inflate_brush(ss, &active_verts); break; case SCULPT_TOOL_GRAB: do_grab_brush(sd, ss); @@ -956,6 +1012,25 @@ static void sculpt_update_tex(Sculpt *sd) } } +void sculptmode_selectbrush_menu(void) +{ + /* XXX: I guess menus belong elsewhere too? + + Sculpt *sd= sculpt_data(); + int val; + + pupmenu_set_active(sd->brush_type); + + val= pupmenu("Select Brush%t|Draw|Smooth|Pinch|Inflate|Grab|Layer|Flatten"); + + if(val>0) { + sd->brush_type= val; + + allqueue(REDRAWVIEW3D, 1); + allqueue(REDRAWBUTSEDIT, 1); + }*/ +} + static void sculptmode_update_all_projverts(SculptSession *ss) { unsigned i; @@ -1034,10 +1109,88 @@ static void sculpt_update_mesh_elements(bContext *C) } } -static int sculpt_mode_poll(bContext *C) +/* XXX: lots of drawing code (partial redraw), has to go elsewhere */ +#if 0 +void sculptmode_draw_wires(SculptSession *ss, int only_damaged) +{ + Mesh *me = get_mesh(OBACT); + int i; + + bglPolygonOffset(1.0); + glDepthMask(0); + BIF_ThemeColor((OBACT==OBACT)?TH_ACTIVE:TH_SELECT); + + for(i=0; i<me->totedge; i++) { + MEdge *med= &me->medge[i]; + + if((!only_damaged || (ss->projverts[med->v1].inside || ss->projverts[med->v2].inside)) && + (med->flag & ME_EDGEDRAW)) { + glDrawElements(GL_LINES, 2, GL_UNSIGNED_INT, &med->v1); + } + } + + glDepthMask(1); + bglPolygonOffset(0.0); +} + +void sculptmode_draw_mesh(int only_damaged) { - return G.f & G_SCULPTMODE; + int i, j, dt, drawCurrentMat = 1, matnr= -1; + SculptSession *ss = sculpt_session(); + + sculpt_update_mesh_elements(ss, OBACT); + + persp(PERSP_VIEW); + mymultmatrix(OBACT->obmat); + glEnable(GL_DEPTH_TEST); + glEnable(GL_LIGHTING); + /* XXX: GPU_set_object_materials(G.scene, OBACT, 0, NULL); */ + glEnable(GL_CULL_FACE); + + glShadeModel(GL_SMOOTH); + + glVertexPointer(3, GL_FLOAT, sizeof(MVert), &cache->mvert[0].co); + glNormalPointer(GL_SHORT, sizeof(MVert), &cache->mvert[0].no); + + dt= MIN2(G.vd->drawtype, OBACT->dt); + if(dt==OB_WIRE) + glColorMask(0,0,0,0); + + for(i=0; i<ss->totface; ++i) { + MFace *f= &ss->mface[i]; + char inside= 0; + int new_matnr= f->mat_nr + 1; + + if(new_matnr != matnr) + drawCurrentMat= GPU_enable_material(matnr = new_matnr, NULL); + + /* If only_damaged!=0, only draw faces that are partially + inside the area(s) modified by the brush */ + if(only_damaged) { + for(j=0; j<(f->v4?4:3); ++j) { + if(ss->projverts[*((&f->v1)+j)].inside) { + inside= 1; + break; + } + } + } + else + inside= 1; + + if(inside && drawCurrentMat) + glDrawElements(f->v4?GL_QUADS:GL_TRIANGLES, f->v4?4:3, GL_UNSIGNED_INT, &f->v1); + } + + glDisable(GL_CULL_FACE); + glDisable(GL_LIGHTING); + glColorMask(1,1,1,1); + + if(dt==OB_WIRE || (OBACT->dtx & OB_DRAWWIRE)) + sculptmode_draw_wires(ss, only_damaged); + + glDisable(GL_DEPTH_TEST); } +#endif static int sculpt_poll(bContext *C) { @@ -1116,7 +1269,7 @@ static void SCULPT_OT_brush_curve_preset(wmOperatorType *ot) ot->idname= "SCULPT_OT_brush_curve_preset"; ot->exec= sculpt_brush_curve_preset_exec; - ot->poll= sculpt_mode_poll; + ot->poll= sculpt_poll; ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; @@ -1181,8 +1334,6 @@ static void sculpt_cache_free(StrokeCache *cache) MEM_freeN(cache->mesh_store); if(cache->orig_norms) MEM_freeN(cache->orig_norms); - if(cache->face_norms) - MEM_freeN(cache->face_norms); if(cache->mats) MEM_freeN(cache->mats); MEM_freeN(cache); @@ -1211,11 +1362,9 @@ static void sculpt_update_cache_invariants(Sculpt *sd, bContext *C, wmOperator * sculpt_update_mesh_elements(C); - if(sd->brush->sculpt_tool == SCULPT_TOOL_LAYER) - cache->layer_disps = MEM_callocN(sizeof(float) * sd->session->totvert, "layer brush displacements"); - /* Make copies of the mesh vertex locations and normals for some tools */ if(sd->brush->sculpt_tool == SCULPT_TOOL_LAYER || (sd->brush->flag & BRUSH_ANCHORED)) { + cache->layer_disps = MEM_callocN(sizeof(float) * sd->session->totvert, "layer brush displacements"); cache->mesh_store= MEM_mallocN(sizeof(float) * 3 * sd->session->totvert, "sculpt mesh vertices copy"); for(i = 0; i < sd->session->totvert; ++i) VecCopyf(cache->mesh_store[i], sd->session->mvert[i].co); @@ -1227,13 +1376,6 @@ static void sculpt_update_cache_invariants(Sculpt *sd, bContext *C, wmOperator * cache->orig_norms[i][1] = sd->session->mvert[i].no[1]; cache->orig_norms[i][2] = sd->session->mvert[i].no[2]; } - - if(sd->session->face_normals) { - float *fn = sd->session->face_normals; - cache->face_norms= MEM_mallocN(sizeof(float) * 3 * sd->session->totface, "Sculpt face norms"); - for(i = 0; i < sd->session->totface; ++i, fn += 3) - VecCopyf(cache->face_norms[i], fn); - } } } @@ -1343,6 +1485,9 @@ static int sculpt_brush_stroke_invoke(bContext *C, wmOperator *op, wmEvent *even Sculpt *sd = CTX_data_tool_settings(C)->sculpt; view3d_operator_needs_opengl(C); + sculpt_brush_stroke_init_properties(C, op, event, sd->session); + + sculptmode_update_all_projverts(sd->session); /* TODO: Shouldn't really have to do this at the start of every stroke, but sculpt would need some sort of notification when @@ -1357,27 +1502,17 @@ static int sculpt_brush_stroke_invoke(bContext *C, wmOperator *op, wmEvent *even static void sculpt_restore_mesh(Sculpt *sd) { - SculptSession *ss = sd->session; - StrokeCache *cache = ss->cache; + StrokeCache *cache = sd->session->cache; int i; /* Restore the mesh before continuing with anchored stroke */ if((sd->brush->flag & BRUSH_ANCHORED) && cache->mesh_store) { - for(i = 0; i < ss->totvert; ++i) { - VecCopyf(ss->mvert[i].co, cache->mesh_store[i]); - ss->mvert[i].no[0] = cache->orig_norms[i][0]; - ss->mvert[i].no[1] = cache->orig_norms[i][1]; - ss->mvert[i].no[2] = cache->orig_norms[i][2]; - } - - if(ss->face_normals) { - float *fn = ss->face_normals; - for(i = 0; i < ss->totface; ++i, fn += 3) - VecCopyf(fn, cache->face_norms[i]); + for(i = 0; i < sd->session->totvert; ++i) { + VecCopyf(sd->session->mvert[i].co, cache->mesh_store[i]); + sd->session->mvert[i].no[0] = cache->orig_norms[i][0]; + sd->session->mvert[i].no[1] = cache->orig_norms[i][1]; + sd->session->mvert[i].no[2] = cache->orig_norms[i][2]; } - - if(sd->brush->sculpt_tool == SCULPT_TOOL_LAYER) - memset(cache->layer_disps, 0, sizeof(float) * ss->totvert); } } @@ -1411,53 +1546,34 @@ static int sculpt_brush_stroke_modal(bContext *C, wmOperator *op, wmEvent *event { PointerRNA itemptr; Sculpt *sd = CTX_data_tool_settings(C)->sculpt; - ARegion *ar = CTX_wm_region(C); float center[3]; int mouse[2] = {event->x, event->y}; - float cur_depth; sculpt_update_mesh_elements(C); - if(!sd->session->cache) { - ViewContext vc; - view3d_set_viewcontext(C, &vc); - cur_depth = read_cached_depth(&vc, event->x, event->y); - - /* Don't start the stroke until a valid depth is found */ - if(cur_depth < 1.0 - FLT_EPSILON) { - sculpt_brush_stroke_init_properties(C, op, event, sd->session); - sculptmode_update_all_projverts(sd->session); - } - - ED_region_tag_redraw(ar); - } + unproject(sd->session->cache->mats, center, event->x, event->y, + read_cached_depth(&sd->session->cache->vc, event->x, event->y)); - if(sd->session->cache) { - cur_depth = read_cached_depth(&sd->session->cache->vc, event->x, event->y); - unproject(sd->session->cache->mats, center, event->x, event->y, cur_depth); + /* Add to stroke */ + RNA_collection_add(op->ptr, "stroke", &itemptr); + RNA_float_set_array(&itemptr, "location", center); + RNA_int_set_array(&itemptr, "mouse", mouse); + RNA_boolean_set(&itemptr, "flip", event->shift); + sculpt_update_cache_variants(sd, &itemptr); - /* Add to stroke */ - RNA_collection_add(op->ptr, "stroke", &itemptr); - RNA_float_set_array(&itemptr, "location", center); - RNA_int_set_array(&itemptr, "mouse", mouse); - RNA_boolean_set(&itemptr, "flip", event->shift); - sculpt_update_cache_variants(sd, &itemptr); - - sculpt_restore_mesh(sd); - do_symmetrical_brush_actions(CTX_data_tool_settings(C)->sculpt, sd->session->cache); + sculpt_restore_mesh(sd); + do_symmetrical_brush_actions(CTX_data_tool_settings(C)->sculpt, sd->session->cache); - sculpt_flush_update(C); - sculpt_post_stroke_free(sd->session); - } + sculpt_flush_update(C); + sculpt_post_stroke_free(sd->session); /* Finished */ if(event->type == LEFTMOUSE && event->val == 0) { - if(sd->session->cache) { - request_depth_update(sd->session->cache->vc.rv3d); - sculpt_cache_free(sd->session->cache); - sd->session->cache = NULL; - sculpt_undo_push(C, sd); - } + request_depth_update(sd->session->cache->vc.rv3d); + + sculpt_cache_free(sd->session->cache); + + sculpt_undo_push(C, sd); return OPERATOR_FINISHED; } @@ -1601,3 +1717,454 @@ void ED_operatortypes_sculpt() WM_operatortype_append(SCULPT_OT_sculptmode_toggle); WM_operatortype_append(SCULPT_OT_brush_curve_preset); } + +void sculpt(Sculpt *sd) +{ +#if 0 + SculptSession *ss= sd->session; + Object *ob= NULL; /*XXX */ + Mesh *me; + MultiresModifierData *mmd = NULL; + /* lastSigMouse is for the rake, to store the last place the mouse movement was significant */ + short mouse[2], mvalo[2], lastSigMouse[2],firsttime=1, mousebut; + short modifier_calculations= 0; + BrushAction *a = MEM_callocN(sizeof(BrushAction), "brush action"); + short spacing= 32000; + int scissor_box[4]; + float offsetRot; + int smooth_stroke = 0, i; + int anchored, rake = 0 /* XXX: rake = ? */; + + /* XXX: checking that sculpting is allowed + if(!(G.f & G_SCULPTMODE) || G.obedit || !ob || ob->id.lib || !get_mesh(ob) || (get_mesh(ob)->totface == 0)) + return; + if(!(ob->lay & G.vd->lay)) + error("Active object is not in this layer"); + if(ob_get_keyblock(ob)) { + if(!(ob->shapeflag & OB_SHAPE_LOCK)) { + error("Cannot sculpt on unlocked shape key"); + return; + } + }*/ + + anchored = sd->brush->flag & BRUSH_ANCHORED; + smooth_stroke = (sd->flags & SCULPT_INPUT_SMOOTH) && (sd->brush->sculpt_tool != SCULPT_TOOL_GRAB) && !anchored; + + if(smooth_stroke) + sculpt_stroke_new(256); + + ss->damaged_rects.first = ss->damaged_rects.last = NULL; + ss->damaged_verts.first = ss->damaged_verts.last = NULL; + ss->vertexcosnos = NULL; + + mmd = sculpt_multires_active(ob); + + /* Check that vertex users are up-to-date */ + if(ob != active_ob || !ss->vertex_users || ss->vertex_users_size != cache->totvert) { + sculpt_vertexusers_free(ss); + calc_vertex_users(ss); + if(ss->projverts) + MEM_freeN(ss->projverts); + ss->projverts = NULL; + active_ob= ob; + } + + glEnableClientState(GL_VERTEX_ARRAY); + glEnableClientState(GL_NORMAL_ARRAY); + + /*XXX: + persp(PERSP_VIEW); + getmouseco_areawin(mvalo);*/ + + /* Init texture + FIXME: Shouldn't be doing this every time! */ + if(sd->tex_mode!=SCULPTREPT_3D) + sculptmode_update_tex(sd); + + /*XXX: getmouseco_areawin(mouse); */ + mvalo[0]= mouse[0]; + mvalo[1]= mouse[1]; + lastSigMouse[0]=mouse[0]; + lastSigMouse[1]=mouse[1]; + mousebut = 0; /* XXX: L_MOUSE; */ + + /* If modifier_calculations is true, then extra time must be spent + updating the mesh. This takes a *lot* longer, so it's worth + skipping if the modifier stack is empty. */ + modifier_calculations= sculpt_modifiers_active(ob); + + if(modifier_calculations) + ss->vertexcosnos= mesh_get_mapped_verts_nors(NULL, ob); /* XXX: scene = ? */ + sculptmode_update_all_projverts(ss); + + /* Capture original copy */ + if(sd->flags & SCULPT_DRAW_FAST) + glAccum(GL_LOAD, 1); + + /* Get original scissor box */ + glGetIntegerv(GL_SCISSOR_BOX, scissor_box); + + /* For raking, get the original angle*/ + offsetRot=sculpt_tex_angle(sd); + + me = get_mesh(ob); + + while (/*XXX:get_mbut() & mousebut*/0) { + /* XXX: getmouseco_areawin(mouse); */ + /* If rake, and the mouse has moved over 10 pixels (euclidean) (prevents jitter) then get the new angle */ + if (rake && (pow(lastSigMouse[0]-mouse[0],2)+pow(lastSigMouse[1]-mouse[1],2))>100){ + /*Nasty looking, but just orig + new angle really*/ + set_tex_angle(sd, offsetRot+180.+to_deg(atan2((float)(mouse[1]-lastSigMouse[1]),(float)(mouse[0]-lastSigMouse[0])))); + lastSigMouse[0]=mouse[0]; + lastSigMouse[1]=mouse[1]; + } + + if(firsttime || mouse[0]!=mvalo[0] || mouse[1]!=mvalo[1] || + sd->brush->flag & BRUSH_AIRBRUSH) { + a->firsttime = firsttime; + firsttime= 0; + + if(smooth_stroke) + sculpt_stroke_add_point(ss->stroke, mouse[0], mouse[1]); + + spacing+= sqrt(pow(mvalo[0]-mouse[0],2)+pow(mvalo[1]-mouse[1],2)); + + if(modifier_calculations && !ss->vertexcosnos) + ss->vertexcosnos= mesh_get_mapped_verts_nors(NULL, ob); /*XXX scene = ? */ + + if(sd->brush->sculpt_tool != SCULPT_TOOL_GRAB) { + if(anchored) { + /* Restore the mesh before continuing with anchored stroke */ + /*if(a->mesh_store) { + for(i = 0; i < cache->totvert; ++i) { + VecCopyf(cache->mvert[i].co, &a->mesh_store[i].x); + cache->mvert[i].no[0] = a->orig_norms[i][0]; + cache->mvert[i].no[1] = a->orig_norms[i][1]; + cache->mvert[i].no[2] = a->orig_norms[i][2]; + } + }*/ + + //do_symmetrical_brush_actions(sd, a, mouse, NULL); + } + else { + if(smooth_stroke) { + sculpt_stroke_apply(sd, ss->stroke); + } + else if(sd->spacing==0 || spacing>sd->spacing) { + //do_symmetrical_brush_actions(sd, a, mouse, NULL); + spacing= 0; + } + } + } + else { + //do_symmetrical_brush_actions(sd, a, mouse, mvalo); + //unproject(ss, sd->pivot, mouse[0], mouse[1], a->depth); + } + + if((!ss->multires && modifier_calculations) || ob_get_keyblock(ob)) { + /* XXX: DAG_object_flush_update(G.scene, ob, OB_RECALC_DATA); */ } + + if(modifier_calculations || sd->brush->sculpt_tool == SCULPT_TOOL_GRAB || !(sd->flags & SCULPT_DRAW_FAST)) { + calc_damaged_verts(ss, a); + /*XXX: scrarea_do_windraw(curarea); + screen_swapbuffers(); */ + } else { /* Optimized drawing */ + calc_damaged_verts(ss, a); + + /* Draw the stored image to the screen */ + glAccum(GL_RETURN, 1); + + sculpt_clear_damaged_areas(ss); + + /* Draw all the polygons that are inside the modified area(s) */ + glScissor(scissor_box[0], scissor_box[1], scissor_box[2], scissor_box[3]); + /* XXX: sculptmode_draw_mesh(1); */ + glAccum(GL_LOAD, 1); + + projverts_clear_inside(ss); + + /* XXX: persp(PERSP_WIN); */ + glDisable(GL_DEPTH_TEST); + + /* Draw cursor */ + if(sd->flags & SCULPT_TOOL_DRAW) + fdrawXORcirc((float)mouse[0],(float)mouse[1],sd->brush->size); + /* XXX: if(smooth_stroke) + sculpt_stroke_draw(); + + myswapbuffers(); */ + } + + BLI_freelistN(&ss->damaged_rects); + ss->damaged_rects.first = ss->damaged_rects.last = NULL; + + mvalo[0]= mouse[0]; + mvalo[1]= mouse[1]; + + if(ss->vertexcosnos) { + MEM_freeN(ss->vertexcosnos); + ss->vertexcosnos= NULL; + } + + } + else { /*XXX:BIF_wait_for_statechange();*/ } + } + + /* Set the rotation of the brush back to what it was before any rake */ + set_tex_angle(sd, offsetRot); + + if(smooth_stroke) { + sculpt_stroke_apply_all(sd, ss->stroke); + calc_damaged_verts(ss, a); + BLI_freelistN(&ss->damaged_rects); + } + + //if(a->layer_disps) MEM_freeN(a->layer_disps); + //if(a->mesh_store) MEM_freeN(a->mesh_store); + //if(a->orig_norms) MEM_freeN(a->orig_norms); + for(i=0; i<8; ++i) + BLI_freelistN(&a->grab_active_verts[i]); + MEM_freeN(a); + sculpt_stroke_free(ss->stroke); + ss->stroke = NULL; + + if(mmd) { + if(mmd->undo_verts && mmd->undo_verts != cache->mvert) + MEM_freeN(mmd->undo_verts); + + mmd->undo_verts = cache->mvert; + mmd->undo_verts_tot = cache->totvert; + } + + //sculpt_undo_push(sd); + + /* XXX: if(G.vd->depths) G.vd->depths->damaged= 1; + allqueue(REDRAWVIEW3D, 0); */ +#endif +} + +/* Partial Mesh Visibility */ + +/* XXX: Partial vis. always was a mess, have to figure something out */ +#if 0 +/* mode: 0=hide outside selection, 1=hide inside selection */ +static void sculptmode_do_pmv(Object *ob, rcti *hb_2d, int mode) +{ + Mesh *me= get_mesh(ob); + float hidebox[6][3]; + vec3f plane_normals[4]; + float plane_ds[4]; + unsigned i, j; + unsigned ndx_show, ndx_hide; + MVert *nve; + unsigned face_cnt_show= 0, face_ndx_show= 0; + unsigned edge_cnt_show= 0, edge_ndx_show= 0; + unsigned *old_map= NULL; + const unsigned SHOW= 0, HIDE=1; + + /* Convert hide box from 2D to 3D */ + unproject(hidebox[0], hb_2d->xmin, hb_2d->ymax, 1); + unproject(hidebox[1], hb_2d->xmax, hb_2d->ymax, 1); + unproject(hidebox[2], hb_2d->xmax, hb_2d->ymin, 1); + unproject(hidebox[3], hb_2d->xmin, hb_2d->ymin, 1); + unproject(hidebox[4], hb_2d->xmin, hb_2d->ymax, 0); + unproject(hidebox[5], hb_2d->xmax, hb_2d->ymin, 0); + + /* Calculate normals for each side of hide box */ + CalcNormFloat(hidebox[0], hidebox[1], hidebox[4], &plane_normals[0].x); + CalcNormFloat(hidebox[1], hidebox[2], hidebox[5], &plane_normals[1].x); + CalcNormFloat(hidebox[2], hidebox[3], hidebox[5], &plane_normals[2].x); + CalcNormFloat(hidebox[3], hidebox[0], hidebox[4], &plane_normals[3].x); + + /* Calculate D for each side of hide box */ + for(i= 0; i<4; ++i) + plane_ds[i]= hidebox[i][0]*plane_normals[i].x + hidebox[i][1]*plane_normals[i].y + + hidebox[i][2]*plane_normals[i].z; + + /* Add partial visibility to mesh */ + if(!me->pv) { + me->pv= MEM_callocN(sizeof(PartialVisibility),"PartialVisibility"); + } else { + old_map= MEM_callocN(sizeof(unsigned)*me->pv->totvert,"PMV oldmap"); + for(i=0; i<me->pv->totvert; ++i) { + old_map[i]= me->pv->vert_map[i]<me->totvert?0:1; + } + mesh_pmv_revert(ob, me); + } + + /* Kill sculpt data */ + active_ob= NULL; + + /* Initalize map with which verts are to be hidden */ + me->pv->vert_map= MEM_mallocN(sizeof(unsigned)*me->totvert, "PMV vertmap"); + me->pv->totvert= me->totvert; + me->totvert= 0; + for(i=0; i<me->pv->totvert; ++i) { + me->pv->vert_map[i]= mode ? HIDE:SHOW; + for(j=0; j<4; ++j) { + if(me->mvert[i].co[0] * plane_normals[j].x + + me->mvert[i].co[1] * plane_normals[j].y + + me->mvert[i].co[2] * plane_normals[j].z < plane_ds[j] ) { + me->pv->vert_map[i]= mode ? SHOW:HIDE; /* Vert is outside the hide box */ + break; + } + } + if(old_map && old_map[i]) me->pv->vert_map[i]= 1; + if(!me->pv->vert_map[i]) ++me->totvert; + + } + if(old_map) MEM_freeN(old_map); + + /* Find out how many faces to show */ + for(i=0; i<me->totface; ++i) { + if(!me->pv->vert_map[me->mface[i].v1] && + !me->pv->vert_map[me->mface[i].v2] && + !me->pv->vert_map[me->mface[i].v3]) { + if(me->mface[i].v4) { + if(!me->pv->vert_map[me->mface[i].v4]) + ++face_cnt_show; + } + else ++face_cnt_show; + } + } + /* Find out how many edges to show */ + for(i=0; i<me->totedge; ++i) { + if(!me->pv->vert_map[me->medge[i].v1] && + !me->pv->vert_map[me->medge[i].v2]) + ++edge_cnt_show; + } + + /* Create new vert array and reset each vert's map with map[old]=new index */ + nve= MEM_mallocN(sizeof(MVert)*me->pv->totvert, "PMV verts"); + ndx_show= 0; ndx_hide= me->totvert; + for(i=0; i<me->pv->totvert; ++i) { + if(me->pv->vert_map[i]) { + me->pv->vert_map[i]= ndx_hide; + nve[me->pv->vert_map[i]]= me->mvert[i]; + ++ndx_hide; + } else { + me->pv->vert_map[i]= ndx_show; + nve[me->pv->vert_map[i]]= me->mvert[i]; + ++ndx_show; + } + } + CustomData_free_layer_active(&me->vdata, CD_MVERT, me->pv->totvert); + me->mvert= CustomData_add_layer(&me->vdata, CD_MVERT, CD_ASSIGN, nve, me->totvert); + + /* Create new face array */ + me->pv->old_faces= me->mface; + me->pv->totface= me->totface; + me->mface= MEM_mallocN(sizeof(MFace)*face_cnt_show, "PMV faces"); + for(i=0; i<me->totface; ++i) { + MFace *pr_f= &me->pv->old_faces[i]; + char show= 0; + + if(me->pv->vert_map[pr_f->v1] < me->totvert && + me->pv->vert_map[pr_f->v2] < me->totvert && + me->pv->vert_map[pr_f->v3] < me->totvert) { + if(pr_f->v4) { + if(me->pv->vert_map[pr_f->v4] < me->totvert) + show= 1; + } + else show= 1; + } + + if(show) { + MFace *cr_f= &me->mface[face_ndx_show]; + *cr_f= *pr_f; + cr_f->v1= me->pv->vert_map[pr_f->v1]; + cr_f->v2= me->pv->vert_map[pr_f->v2]; + cr_f->v3= me->pv->vert_map[pr_f->v3]; + cr_f->v4= pr_f->v4 ? me->pv->vert_map[pr_f->v4] : 0; + test_index_face(cr_f,NULL,0,pr_f->v4?4:3); + ++face_ndx_show; + } + } + me->totface= face_cnt_show; + CustomData_set_layer(&me->fdata, CD_MFACE, me->mface); + + /* Create new edge array */ + me->pv->old_edges= me->medge; + me->pv->totedge= me->totedge; + me->medge= MEM_mallocN(sizeof(MEdge)*edge_cnt_show, "PMV edges"); + me->pv->edge_map= MEM_mallocN(sizeof(int)*me->pv->totedge,"PMV edgemap"); + for(i=0; i<me->totedge; ++i) { + if(me->pv->vert_map[me->pv->old_edges[i].v1] < me->totvert && + me->pv->vert_map[me->pv->old_edges[i].v2] < me->totvert) { + MEdge *cr_e= &me->medge[edge_ndx_show]; + me->pv->edge_map[i]= edge_ndx_show; + *cr_e= me->pv->old_edges[i]; + cr_e->v1= me->pv->vert_map[me->pv->old_edges[i].v1]; + cr_e->v2= me->pv->vert_map[me->pv->old_edges[i].v2]; + ++edge_ndx_show; + } + else me->pv->edge_map[i]= -1; + } + me->totedge= edge_cnt_show; + CustomData_set_layer(&me->edata, CD_MEDGE, me->medge); + + /* XXX: DAG_object_flush_update(G.scene, OBACT, OB_RECALC_DATA); */ +} + +static rcti sculptmode_pmv_box() +{ + /*XXX: short down[2], mouse[2]; + rcti ret; + + getmouseco_areawin(down); + + while((get_mbut()&L_MOUSE) || (get_mbut()&R_MOUSE)) { + getmouseco_areawin(mouse); + + scrarea_do_windraw(curarea); + + persp(PERSP_WIN); + glLineWidth(2); + setlinestyle(2); + sdrawXORline(down[0],down[1],mouse[0],down[1]); + sdrawXORline(mouse[0],down[1],mouse[0],mouse[1]); + sdrawXORline(mouse[0],mouse[1],down[0],mouse[1]); + sdrawXORline(down[0],mouse[1],down[0],down[1]); + setlinestyle(0); + glLineWidth(1); + persp(PERSP_VIEW); + + screen_swapbuffers(); + backdrawview3d(0); + } + + ret.xmin= down[0]<mouse[0]?down[0]:mouse[0]; + ret.ymin= down[1]<mouse[1]?down[1]:mouse[1]; + ret.xmax= down[0]>mouse[0]?down[0]:mouse[0]; + ret.ymax= down[1]>mouse[1]?down[1]:mouse[1]; + return ret;*/ +} + +void sculptmode_pmv(int mode) +{ + Object *ob= NULL; /*XXX: OBACT; */ + rcti hb_2d; + + if(ob_get_key(ob)) { + error("Cannot hide mesh with shape keys enabled"); + return; + } + + hb_2d= sculptmode_pmv_box(); /* Get 2D hide box */ + + sculptmode_correct_state(); + + waitcursor(1); + + if(hb_2d.xmax-hb_2d.xmin > 3 && hb_2d.ymax-hb_2d.ymin > 3) { + init_sculptmatrices(); + + sculptmode_do_pmv(ob,&hb_2d,mode); + } + else mesh_pmv_off(ob, get_mesh(ob)); + + /*XXX: scrarea_do_windraw(curarea); */ + + waitcursor(0); +} +#endif diff --git a/source/blender/editors/sculpt_paint/sculpt_intern.h b/source/blender/editors/sculpt_paint/sculpt_intern.h index febca301939..112da5b4f0f 100644 --- a/source/blender/editors/sculpt_paint/sculpt_intern.h +++ b/source/blender/editors/sculpt_paint/sculpt_intern.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: BDR_sculptmode.h 13396 2008-01-25 04:17:38Z nicholasbishop $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/sculpt_paint/sculpt_stroke.c b/source/blender/editors/sculpt_paint/sculpt_stroke.c index 554ff580358..1c23ec2a546 100644 --- a/source/blender/editors/sculpt_paint/sculpt_stroke.c +++ b/source/blender/editors/sculpt_paint/sculpt_stroke.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: sculpt_stroke.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_action/Makefile b/source/blender/editors/space_action/Makefile index e856587acca..840f31b8a40 100644 --- a/source/blender/editors/space_action/Makefile +++ b/source/blender/editors/space_action/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_action/action_draw.c b/source/blender/editors/space_action/action_draw.c index 2c9f91e0941..6eae581aa40 100644 --- a/source/blender/editors/space_action/action_draw.c +++ b/source/blender/editors/space_action/action_draw.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: drawaction.c 17746 2008-12-08 11:19:44Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_action/action_edit.c b/source/blender/editors/space_action/action_edit.c index 5d262cb03c5..a0f1adbd97e 100644 --- a/source/blender/editors/space_action/action_edit.c +++ b/source/blender/editors/space_action/action_edit.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: editaction.c 17746 2008-12-08 11:19:44Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_action/action_select.c b/source/blender/editors/space_action/action_select.c index 06f35f5cf05..b82e44f3aa3 100644 --- a/source/blender/editors/space_action/action_select.c +++ b/source/blender/editors/space_action/action_select.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: editaction.c 17746 2008-12-08 11:19:44Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_api/Makefile b/source/blender/editors/space_api/Makefile index 474fbe89053..46f926afbc9 100644 --- a/source/blender/editors/space_api/Makefile +++ b/source/blender/editors/space_api/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_api/spacetypes.c b/source/blender/editors/space_api/spacetypes.c index 510103895f4..4f9c1f4b7a7 100644 --- a/source/blender/editors/space_api/spacetypes.c +++ b/source/blender/editors/space_api/spacetypes.c @@ -50,7 +50,6 @@ #include "ED_screen.h" #include "ED_space_api.h" #include "ED_uvedit.h" -#include "ED_pointcache.h" /* only call once on startup, storage is global in BKE kernel listbase */ void ED_spacetypes_init(void) @@ -90,7 +89,6 @@ void ED_spacetypes_init(void) ED_operatortypes_curve(); ED_operatortypes_armature(); ED_marker_operatortypes(); - ED_operatortypes_pointcache(); ui_view2d_operatortypes(); diff --git a/source/blender/editors/space_buttons/Makefile b/source/blender/editors/space_buttons/Makefile index a4894ede06b..b96d1cc5495 100644 --- a/source/blender/editors/space_buttons/Makefile +++ b/source/blender/editors/space_buttons/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_buttons/SConscript b/source/blender/editors/space_buttons/SConscript index a0a7dad4077..541da52f7f9 100644 --- a/source/blender/editors/space_buttons/SConscript +++ b/source/blender/editors/space_buttons/SConscript @@ -12,4 +12,7 @@ defs = [] if env['WITH_BF_GAMEENGINE']: defs.append('GAMEBLENDER=1') + if env['WITH_BF_SOLID']: + defs.append('USE_SUMO_SOLID') + env.BlenderLib ( 'bf_editors_space_buttons', sources, Split(incs), defs, libtype=['core'], priority=[120] ) diff --git a/source/blender/editors/space_buttons/buttons_context.c b/source/blender/editors/space_buttons/buttons_context.c index 01794d1bba8..d97b4acdb96 100644 --- a/source/blender/editors/space_buttons/buttons_context.c +++ b/source/blender/editors/space_buttons/buttons_context.c @@ -552,7 +552,7 @@ int buttons_context(const bContext *C, const char *member, bContextDataResult *r if(ptr) { Object *ob= ptr->data; - if(ob && ob->type && (ob->type<OB_LAMP) && ob->totcol) + if(ob && ob->type && (ob->type<OB_LAMP)) CTX_data_pointer_set(result, &ob->id, &RNA_MaterialSlot, ob->mat+ob->actcol-1); } @@ -668,6 +668,7 @@ void buttons_context_draw(const bContext *C, uiLayout *layout) uiBlock *block; uiBut *but; PointerRNA *ptr; + PropertyRNA *nameprop; char namebuf[128], *name; int a, icon; @@ -687,7 +688,7 @@ void buttons_context_draw(const bContext *C, uiLayout *layout) if(ptr->data) { icon= RNA_struct_ui_icon(ptr->type); - name= RNA_struct_name_get_alloc(ptr, namebuf, sizeof(namebuf)); + nameprop= RNA_struct_name_property(ptr->type); #if 0 if(sbuts->mainb != BCONTEXT_SCENE && ptr->type == &RNA_Scene) { @@ -695,7 +696,9 @@ void buttons_context_draw(const bContext *C, uiLayout *layout) } else #endif - if(name) { + if(nameprop) { + name= RNA_property_string_get_alloc(ptr, nameprop, namebuf, sizeof(namebuf)); + uiItemL(row, name, icon); if(name != namebuf) diff --git a/source/blender/editors/space_buttons/buttons_header.c b/source/blender/editors/space_buttons/buttons_header.c index 7c622f172a2..98fd198d84b 100644 --- a/source/blender/editors/space_buttons/buttons_header.c +++ b/source/blender/editors/space_buttons/buttons_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: buttons_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -173,10 +173,10 @@ void buttons_header_buttons(const bContext *C, ARegion *ar) uiDefIconButS(block, ROW, B_CONTEXT_SWITCH, ICON_OBJECT_DATA, xco+=XIC, yco, XIC, YIC, &(sbuts->mainb), 0.0, (float)BCONTEXT_OBJECT, 0, 0, "Object"); if(sbuts->pathflag & (1<<BCONTEXT_CONSTRAINT)) uiDefIconButS(block, ROW, B_CONTEXT_SWITCH, ICON_CONSTRAINT, xco+=XIC, yco, XIC, YIC, &(sbuts->mainb), 0.0, (float)BCONTEXT_CONSTRAINT, 0, 0, "Constraint"); - if(sbuts->pathflag & (1<<BCONTEXT_DATA)) - uiDefIconButS(block, ROW, B_CONTEXT_SWITCH, sbuts->dataicon, xco+=XIC, yco, XIC, YIC, &(sbuts->mainb), 0.0, (float)BCONTEXT_DATA, 0, 0, "Object Data"); if(sbuts->pathflag & (1<<BCONTEXT_MODIFIER)) uiDefIconButS(block, ROW, B_CONTEXT_SWITCH, ICON_MODIFIER, xco+=XIC, yco, XIC, YIC, &(sbuts->mainb), 0.0, (float)BCONTEXT_MODIFIER, 0, 0, "Modifier"); + if(sbuts->pathflag & (1<<BCONTEXT_DATA)) + uiDefIconButS(block, ROW, B_CONTEXT_SWITCH, sbuts->dataicon, xco+=XIC, yco, XIC, YIC, &(sbuts->mainb), 0.0, (float)BCONTEXT_DATA, 0, 0, "Object Data"); if(sbuts->pathflag & (1<<BCONTEXT_BONE)) uiDefIconButS(block, ROW, B_CONTEXT_SWITCH, ICON_BONE_DATA, xco+=XIC, yco, XIC, YIC, &(sbuts->mainb), 0.0, (float)BCONTEXT_BONE, 0, 0, "Bone"); if(sbuts->pathflag & (1<<BCONTEXT_MATERIAL)) diff --git a/source/blender/editors/space_buttons/buttons_intern.h b/source/blender/editors/space_buttons/buttons_intern.h index 13ea778fb00..196647a3750 100644 --- a/source/blender/editors/space_buttons/buttons_intern.h +++ b/source/blender/editors/space_buttons/buttons_intern.h @@ -61,20 +61,9 @@ void buttons_context_draw(const struct bContext *C, struct uiLayout *layout); void buttons_context_register(struct ARegionType *art); /* buttons_ops.c */ -void OBJECT_OT_material_slot_add(struct wmOperatorType *ot); -void OBJECT_OT_material_slot_remove(struct wmOperatorType *ot); -void OBJECT_OT_material_slot_assign(struct wmOperatorType *ot); -void OBJECT_OT_material_slot_select(struct wmOperatorType *ot); -void OBJECT_OT_material_slot_deselect(struct wmOperatorType *ot); - void MATERIAL_OT_new(struct wmOperatorType *ot); void TEXTURE_OT_new(struct wmOperatorType *ot); void WORLD_OT_new(struct wmOperatorType *ot); -void OBJECT_OT_particle_system_slot_add(struct wmOperatorType *ot); -void OBJECT_OT_particle_system_slot_remove(struct wmOperatorType *ot); - -void PARTICLE_OT_new(struct wmOperatorType *ot); - #endif /* ED_BUTTONS_INTERN_H */ diff --git a/source/blender/editors/space_buttons/buttons_ops.c b/source/blender/editors/space_buttons/buttons_ops.c index 6ca92674c6e..63469a8294d 100644 --- a/source/blender/editors/space_buttons/buttons_ops.c +++ b/source/blender/editors/space_buttons/buttons_ops.c @@ -30,7 +30,6 @@ #include "MEM_guardedalloc.h" -#include "DNA_curve_types.h" #include "DNA_object_types.h" #include "DNA_material_types.h" #include "DNA_texture_types.h" @@ -38,251 +37,31 @@ #include "DNA_world_types.h" #include "BKE_context.h" -#include "BKE_depsgraph.h" -#include "BKE_font.h" #include "BKE_library.h" #include "BKE_material.h" -#include "BKE_particle.h" #include "BKE_texture.h" -#include "BKE_utildefines.h" #include "BKE_world.h" -#include "BLI_editVert.h" - #include "RNA_access.h" #include "WM_api.h" #include "WM_types.h" -#include "ED_curve.h" -#include "ED_mesh.h" - #include "buttons_intern.h" // own include -/********************** material slot operators *********************/ - -static int material_slot_add_exec(bContext *C, wmOperator *op) -{ - Object *ob= CTX_data_pointer_get_type(C, "object", &RNA_Object).data; - - if(!ob) - return OPERATOR_CANCELLED; - - object_add_material_slot(ob); - WM_event_add_notifier(C, NC_OBJECT|ND_DRAW, ob); - - return OPERATOR_FINISHED; -} - -void OBJECT_OT_material_slot_add(wmOperatorType *ot) -{ - /* identifiers */ - ot->name= "Add Material Slot"; - ot->idname= "OBJECT_OT_material_slot_add"; - - /* api callbacks */ - ot->exec= material_slot_add_exec; - - /* flags */ - ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; -} - -static int material_slot_remove_exec(bContext *C, wmOperator *op) -{ - Object *ob= CTX_data_pointer_get_type(C, "object", &RNA_Object).data; - - if(!ob) - return OPERATOR_CANCELLED; - - object_remove_material_slot(ob); - WM_event_add_notifier(C, NC_OBJECT|ND_DRAW, ob); - - return OPERATOR_FINISHED; -} - -void OBJECT_OT_material_slot_remove(wmOperatorType *ot) -{ - /* identifiers */ - ot->name= "Remove Material Slot"; - ot->idname= "OBJECT_OT_material_slot_remove"; - - /* api callbacks */ - ot->exec= material_slot_remove_exec; - - /* flags */ - ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; -} - -static int material_slot_assign_exec(bContext *C, wmOperator *op) -{ - Scene *scene= CTX_data_scene(C); - Object *ob= CTX_data_pointer_get_type(C, "object", &RNA_Object).data; - - if(!ob) - return OPERATOR_CANCELLED; - - if(ob && ob->actcol>0) { - if(ob->type == OB_MESH) { - EditMesh *em= ((Mesh*)ob->data)->edit_mesh; - EditFace *efa; - - if(em) { - for(efa= em->faces.first; efa; efa=efa->next) - if(efa->f & SELECT) - efa->mat_nr= ob->actcol-1; - } - } - else if(ELEM(ob->type, OB_CURVE, OB_SURF)) { - ListBase *editnurb= ((Curve*)ob->data)->editnurb; - Nurb *nu; - - if(editnurb) { - for(nu= editnurb->first; nu; nu= nu->next) - if(isNurbsel(nu)) - nu->mat_nr= nu->charidx= ob->actcol-1; - } - } - else if(ob->type == OB_FONT) { - EditFont *ef= ((Curve*)ob->data)->editfont; - int i, selstart, selend; - - if(ef && BKE_font_getselection(ob, &selstart, &selend)) { - for(i=selstart; i<=selend; i++) - ef->textbufinfo[i].mat_nr = ob->actcol-1; - } - } - } - - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); - WM_event_add_notifier(C, NC_OBJECT|ND_GEOM_DATA, ob); - - return OPERATOR_FINISHED; -} - -void OBJECT_OT_material_slot_assign(wmOperatorType *ot) -{ - /* identifiers */ - ot->name= "Assign Material Slot"; - ot->idname= "OBJECT_OT_material_slot_assign"; - - /* api callbacks */ - ot->exec= material_slot_assign_exec; - - /* flags */ - ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; -} - -static int material_slot_de_select(bContext *C, int select) -{ - Object *ob= CTX_data_pointer_get_type(C, "object", &RNA_Object).data; - - if(!ob) - return OPERATOR_CANCELLED; - - if(ob->type == OB_MESH) { - EditMesh *em= ((Mesh*)ob->data)->edit_mesh; - - if(em) { - if(select) - EM_select_by_material(em, ob->actcol-1); - else - EM_deselect_by_material(em, ob->actcol-1); - } - } - else if ELEM(ob->type, OB_CURVE, OB_SURF) { - ListBase *editnurb= ((Curve*)ob->data)->editnurb; - Nurb *nu; - BPoint *bp; - BezTriple *bezt; - int a; - - for(nu= editnurb->first; nu; nu=nu->next) { - if(nu->mat_nr==ob->actcol-1) { - if(nu->bezt) { - a= nu->pntsu; - bezt= nu->bezt; - while(a--) { - if(bezt->hide==0) { - if(select) { - bezt->f1 |= SELECT; - bezt->f2 |= SELECT; - bezt->f3 |= SELECT; - } - else { - bezt->f1 &= ~SELECT; - bezt->f2 &= ~SELECT; - bezt->f3 &= ~SELECT; - } - } - bezt++; - } - } - else if(nu->bp) { - a= nu->pntsu*nu->pntsv; - bp= nu->bp; - while(a--) { - if(bp->hide==0) { - if(select) bp->f1 |= SELECT; - else bp->f1 &= ~SELECT; - } - bp++; - } - } - } - } - } - - WM_event_add_notifier(C, NC_OBJECT|ND_GEOM_SELECT, ob); - - return OPERATOR_FINISHED; -} - -static int material_slot_select_exec(bContext *C, wmOperator *op) -{ - return material_slot_de_select(C, 1); -} - -void OBJECT_OT_material_slot_select(wmOperatorType *ot) -{ - /* identifiers */ - ot->name= "Select Material Slot"; - ot->idname= "OBJECT_OT_material_slot_select"; - - /* api callbacks */ - ot->exec= material_slot_select_exec; - - /* flags */ - ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; -} - -static int material_slot_deselect_exec(bContext *C, wmOperator *op) -{ - return material_slot_de_select(C, 0); -} - -void OBJECT_OT_material_slot_deselect(wmOperatorType *ot) -{ - /* identifiers */ - ot->name= "Deselect Material Slot"; - ot->idname= "OBJECT_OT_material_slot_deselect"; - - /* api callbacks */ - ot->exec= material_slot_deselect_exec; - - /* flags */ - ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; -} - /********************** new material operator *********************/ static int new_material_exec(bContext *C, wmOperator *op) { - Material *ma= CTX_data_pointer_get_type(C, "material", &RNA_Material).data; - Object *ob; PointerRNA ptr; + Material *ma; + Object *ob; int index; /* add or copy material */ + ptr= CTX_data_pointer_get(C, "material"); + ma= (RNA_struct_is_a(ptr.type, &RNA_Material))? ptr.data: NULL; + if(ma) ma= copy_material(ma); else @@ -291,9 +70,9 @@ static int new_material_exec(bContext *C, wmOperator *op) ma->id.us--; /* compensating for us++ in assign_material */ /* attempt to assign to material slot */ - ptr= CTX_data_pointer_get_type(C, "material_slot", &RNA_MaterialSlot); + ptr= CTX_data_pointer_get(C, "material_slot"); - if(ptr.data) { + if(RNA_struct_is_a(ptr.type, &RNA_MaterialSlot)) { ob= ptr.id.data; index= (Material**)ptr.data - ob->mat; @@ -301,8 +80,6 @@ static int new_material_exec(bContext *C, wmOperator *op) WM_event_add_notifier(C, NC_OBJECT|ND_DRAW, ob); } - - WM_event_add_notifier(C, NC_MATERIAL|NA_ADDED, ma); return OPERATOR_FINISHED; } @@ -324,12 +101,15 @@ void MATERIAL_OT_new(wmOperatorType *ot) static int new_texture_exec(bContext *C, wmOperator *op) { - Tex *tex= CTX_data_pointer_get_type(C, "texture", &RNA_Texture).data; + PointerRNA ptr; ID *id; + Tex *tex; MTex *mtex; - PointerRNA ptr; /* add or copy texture */ + ptr= CTX_data_pointer_get(C, "texture"); + tex= (RNA_struct_is_a(ptr.type, &RNA_Texture))? ptr.data: NULL; + if(tex) tex= copy_texture(tex); else @@ -338,9 +118,9 @@ static int new_texture_exec(bContext *C, wmOperator *op) id_us_min(&tex->id); /* attempt to assign to texture slot */ - ptr= CTX_data_pointer_get_type(C, "texture_slot", &RNA_TextureSlot); + ptr= CTX_data_pointer_get(C, "texture_slot"); - if(ptr.data) { + if(RNA_struct_is_a(ptr.type, &RNA_TextureSlot)) { id= ptr.id.data; mtex= ptr.data; @@ -353,8 +133,6 @@ static int new_texture_exec(bContext *C, wmOperator *op) /* XXX nodes, notifier .. */ } - - WM_event_add_notifier(C, NC_TEXTURE|NA_ADDED, tex); return OPERATOR_FINISHED; } @@ -376,21 +154,27 @@ void TEXTURE_OT_new(wmOperatorType *ot) static int new_world_exec(bContext *C, wmOperator *op) { - Scene *scene= CTX_data_scene(C); - World *wo= CTX_data_pointer_get_type(C, "world", &RNA_World).data; + PointerRNA ptr; + Scene *scene; + World *wo; /* add or copy world */ + ptr= CTX_data_pointer_get(C, "world"); + wo= (RNA_struct_is_a(ptr.type, &RNA_World))? ptr.data: NULL; + if(wo) wo= copy_world(wo); else wo= add_world("World"); /* assign to scene */ + scene= CTX_data_scene(C); + if(scene->world) id_us_min(&scene->world->id); scene->world= wo; - WM_event_add_notifier(C, NC_WORLD|NA_ADDED, wo); + // XXX notifier return OPERATOR_FINISHED; } @@ -408,109 +192,3 @@ void WORLD_OT_new(wmOperatorType *ot) ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; } - - -/********************** particle system slot operators *********************/ - -static int particle_system_slot_add_exec(bContext *C, wmOperator *op) -{ - Object *ob= CTX_data_pointer_get_type(C, "object", &RNA_Object).data; - Scene *scene = CTX_data_scene(C); - - if(!scene || !ob) - return OPERATOR_CANCELLED; - - object_add_particle_system_slot(scene, ob); - WM_event_add_notifier(C, NC_OBJECT|ND_DRAW, ob); - - return OPERATOR_FINISHED; -} - -void OBJECT_OT_particle_system_slot_add(wmOperatorType *ot) -{ - /* identifiers */ - ot->name= "Add Particle System Slot"; - ot->idname= "OBJECT_OT_particle_system_slot_add"; - - /* api callbacks */ - ot->exec= particle_system_slot_add_exec; - - /* flags */ - ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; -} - -static int particle_system_slot_remove_exec(bContext *C, wmOperator *op) -{ - Object *ob= CTX_data_pointer_get_type(C, "object", &RNA_Object).data; - Scene *scene = CTX_data_scene(C); - - if(!scene || !ob) - return OPERATOR_CANCELLED; - - object_remove_particle_system_slot(scene, ob); - WM_event_add_notifier(C, NC_OBJECT|ND_DRAW, ob); - - return OPERATOR_FINISHED; -} - -void OBJECT_OT_particle_system_slot_remove(wmOperatorType *ot) -{ - /* identifiers */ - ot->name= "Remove Particle System Slot"; - ot->idname= "OBJECT_OT_particle_system_slot_remove"; - - /* api callbacks */ - ot->exec= particle_system_slot_remove_exec; - - /* flags */ - ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; -} - -/********************** new particle settings operator *********************/ - -static int new_particle_settings_exec(bContext *C, wmOperator *op) -{ - Scene *scene = CTX_data_scene(C); - ParticleSettings *part= CTX_data_pointer_get_type(C, "particle_settings", &RNA_ParticleSettings).data; - Object *ob; - PointerRNA ptr; - - /* add or copy particle setting */ - if(part) - part= psys_copy_settings(part); - else - part= psys_new_settings("PSys", NULL); - - /* attempt to assign to material slot */ - ptr= CTX_data_pointer_get_type(C, "particle_system", &RNA_ParticleSystem); - - if(ptr.data) { - ParticleSystem *psys = (ParticleSystem*)ptr.data; - ob= ptr.id.data; - - if(psys->part) - psys->part->id.us--; - - psys->part = part; - - DAG_scene_sort(scene); - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); - - WM_event_add_notifier(C, NC_OBJECT|ND_DRAW, ob); - } - - return OPERATOR_FINISHED; -} - -void PARTICLE_OT_new(wmOperatorType *ot) -{ - /* identifiers */ - ot->name= "New Particle Settings"; - ot->idname= "PARTICLE_OT_new"; - - /* api callbacks */ - ot->exec= new_particle_settings_exec; - - /* flags */ - ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; -} diff --git a/source/blender/editors/space_buttons/space_buttons.c b/source/blender/editors/space_buttons/space_buttons.c index 7954d5254cc..38ce88019ed 100644 --- a/source/blender/editors/space_buttons/space_buttons.c +++ b/source/blender/editors/space_buttons/space_buttons.c @@ -210,20 +210,9 @@ static void buttons_main_area_draw(const bContext *C, ARegion *ar) void buttons_operatortypes(void) { - WM_operatortype_append(OBJECT_OT_material_slot_add); - WM_operatortype_append(OBJECT_OT_material_slot_remove); - WM_operatortype_append(OBJECT_OT_material_slot_assign); - WM_operatortype_append(OBJECT_OT_material_slot_select); - WM_operatortype_append(OBJECT_OT_material_slot_deselect); - WM_operatortype_append(MATERIAL_OT_new); WM_operatortype_append(TEXTURE_OT_new); WM_operatortype_append(WORLD_OT_new); - - WM_operatortype_append(OBJECT_OT_particle_system_slot_add); - WM_operatortype_append(OBJECT_OT_particle_system_slot_remove); - - WM_operatortype_append(PARTICLE_OT_new); } void buttons_keymap(struct wmWindowManager *wm) @@ -231,23 +220,14 @@ void buttons_keymap(struct wmWindowManager *wm) } -//#define PY_HEADER /* add handlers, stuff you only do once or on area/region changes */ static void buttons_header_area_init(wmWindowManager *wm, ARegion *ar) { -#ifdef PY_HEADER - ED_region_header_init(ar); -#else UI_view2d_region_reinit(&ar->v2d, V2D_COMMONVIEW_HEADER, ar->winx, ar->winy); -#endif } static void buttons_header_area_draw(const bContext *C, ARegion *ar) { -#ifdef PY_HEADER - ED_region_header(C, ar); -#else - float col[3]; /* clear */ @@ -263,8 +243,7 @@ static void buttons_header_area_draw(const bContext *C, ARegion *ar) UI_view2d_view_ortho(C, &ar->v2d); buttons_header_buttons(C, ar); -#endif - + /* restore view matrix? */ UI_view2d_view_restore(C); } @@ -348,11 +327,6 @@ static void buttons_area_listener(ScrArea *sa, wmNotifier *wmn) case ND_GEOM_SELECT: ED_area_tag_redraw(sa); break; - case ND_SHADING: - case ND_SHADING_DRAW: - /* currently works by redraws... if preview is set, it (re)starts job */ - sbuts->preview= 1; - break; } break; case NC_MATERIAL: @@ -363,6 +337,7 @@ static void buttons_area_listener(ScrArea *sa, wmNotifier *wmn) case ND_SHADING_DRAW: /* currently works by redraws... if preview is set, it (re)starts job */ sbuts->preview= 1; + printf("shader notifier \n"); break; } break; diff --git a/source/blender/editors/space_file/Makefile b/source/blender/editors/space_file/Makefile index 2f4180448e5..8f48217473c 100644 --- a/source/blender/editors/space_file/Makefile +++ b/source/blender/editors/space_file/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_file/file_draw.c b/source/blender/editors/space_file/file_draw.c index bb47d3458fe..6ed8f87d987 100644 --- a/source/blender/editors/space_file/file_draw.c +++ b/source/blender/editors/space_file/file_draw.c @@ -550,24 +550,7 @@ void file_draw_list(const bContext *C, ARegion *ar) } } -static void file_draw_fsmenu_category_name(ARegion *ar, const char *category_name, short *starty) -{ - short sx, sy; - int bmwidth = ar->v2d.cur.xmax - ar->v2d.cur.xmin - 2*TILE_BORDER_X - ICON_DEFAULT_WIDTH - 4; - int fontsize = file_font_pointsize(); - - sx = ar->v2d.cur.xmin + TILE_BORDER_X; - sy = *starty; - - UI_ThemeColor(TH_TEXT_HI); - file_draw_string(sx, sy, category_name, bmwidth, fontsize, FILE_SHORTEN_END); - - sy -= fontsize*2.0f; - - *starty= sy; -} - -static void file_draw_fsmenu_category(const bContext *C, ARegion *ar, FSMenuCategory category, short *starty) +static void file_draw_fsmenu_category(const bContext *C, ARegion *ar, FSMenuCategory category, const char* category_name, short *starty) { struct FSMenu* fsmenu = fsmenu_get(); char bookmark[FILE_MAX]; @@ -582,6 +565,11 @@ static void file_draw_fsmenu_category(const bContext *C, ARegion *ar, FSMenuCate sx = ar->v2d.cur.xmin + TILE_BORDER_X; sy = *starty; + UI_ThemeColor(TH_TEXT_HI); + file_draw_string(sx, sy, category_name, bmwidth, fontsize, FILE_SHORTEN_END); + + sy -= fontsize*2.0f; + switch(category) { case FS_CATEGORY_SYSTEM: cat_icon = ICON_DISK_DRIVE; break; @@ -628,54 +616,15 @@ static void file_draw_fsmenu_category(const bContext *C, ARegion *ar, FSMenuCate *starty = sy; } -void file_draw_fsmenu_operator(const bContext *C, ARegion *ar, wmOperator *op, short *starty) -{ - uiStyle *style= U.uistyles.first; - uiBlock *block; - uiLayout *layout; - int sy; - - sy= *starty; - - block= uiBeginBlock(C, ar, "file_options", UI_EMBOSS); - layout= uiBlockLayout(block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, TILE_BORDER_X, sy, ar->winx-2*TILE_BORDER_X, 20, style); - - RNA_STRUCT_BEGIN(op->ptr, prop) { - if(strcmp(RNA_property_identifier(prop), "rna_type") == 0) - continue; - if(strcmp(RNA_property_identifier(prop), "filename") == 0) - continue; - - uiItemFullR(layout, NULL, 0, op->ptr, prop, -1, 0, 0, 0, 0); - } - RNA_STRUCT_END; - - uiBlockLayoutResolve(C, block, NULL, &sy); - uiEndBlock(C, block); - uiDrawBlock(C, block); - - *starty= sy; -} - void file_draw_fsmenu(const bContext *C, ARegion *ar) { - SpaceFile *sfile= (SpaceFile*)CTX_wm_space_data(C); int linestep = file_font_pointsize()*2.0f; short sy= ar->v2d.cur.ymax-2*TILE_BORDER_Y; - file_draw_fsmenu_category_name(ar, "SYSTEM", &sy); - file_draw_fsmenu_category(C, ar, FS_CATEGORY_SYSTEM, &sy); + file_draw_fsmenu_category(C, ar, FS_CATEGORY_SYSTEM, "SYSTEM", &sy); sy -= linestep; - file_draw_fsmenu_category_name(ar, "BOOKMARKS", &sy); - file_draw_fsmenu_category(C, ar, FS_CATEGORY_BOOKMARKS, &sy); + file_draw_fsmenu_category(C, ar, FS_CATEGORY_BOOKMARKS, "BOOKMARKS", &sy); sy -= linestep; - file_draw_fsmenu_category_name(ar, "RECENT", &sy); - file_draw_fsmenu_category(C, ar, FS_CATEGORY_RECENT, &sy); - - if(sfile->op) { - sy -= linestep; - file_draw_fsmenu_category_name(ar, "OPTIONS", &sy); - file_draw_fsmenu_operator(C, ar, sfile->op, &sy); - } + file_draw_fsmenu_category(C, ar, FS_CATEGORY_RECENT, "RECENT", &sy); + } - diff --git a/source/blender/editors/space_file/file_header.c b/source/blender/editors/space_file/file_header.c index 4799003d6c7..34374268d5c 100644 --- a/source/blender/editors/space_file/file_header.c +++ b/source/blender/editors/space_file/file_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: file_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_file/file_ops.c b/source/blender/editors/space_file/file_ops.c index ab02147d020..0c6cadc05c1 100644 --- a/source/blender/editors/space_file/file_ops.c +++ b/source/blender/editors/space_file/file_ops.c @@ -190,7 +190,7 @@ static int file_border_select_exec(bContext *C, wmOperator *op) rect.xmax= RNA_int_get(op->ptr, "xmax"); rect.ymax= RNA_int_get(op->ptr, "ymax"); - BLI_isect_rcti(&(ar->v2d.mask), &rect, &rect); + BLI_isect_rctf(&(ar->v2d.mask), &rect, &rect); file_select(sfile, ar, &rect, val ); WM_event_add_notifier(C, NC_WINDOW, NULL); diff --git a/source/blender/editors/space_file/filesel.c b/source/blender/editors/space_file/filesel.c index 479d9cabc55..d57fc7f90bc 100644 --- a/source/blender/editors/space_file/filesel.c +++ b/source/blender/editors/space_file/filesel.c @@ -159,7 +159,7 @@ float file_string_width(const char* str) { uiStyle *style= U.uistyles.first; uiStyleFontSet(&style->widget); - return BLF_width((char *)str); + return BLF_width(str); } float file_font_pointsize() diff --git a/source/blender/editors/space_graph/Makefile b/source/blender/editors/space_graph/Makefile index e04a354fb1d..340495ecc79 100644 --- a/source/blender/editors/space_graph/Makefile +++ b/source/blender/editors/space_graph/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_graph/graph_draw.c b/source/blender/editors/space_graph/graph_draw.c index ddf4105fdf4..acf712d0147 100644 --- a/source/blender/editors/space_graph/graph_draw.c +++ b/source/blender/editors/space_graph/graph_draw.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: drawipo.c 17512 2008-11-20 05:55:42Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_graph/graph_edit.c b/source/blender/editors/space_graph/graph_edit.c index b624d02a633..49397ed0edd 100644 --- a/source/blender/editors/space_graph/graph_edit.c +++ b/source/blender/editors/space_graph/graph_edit.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: editaction.c 17746 2008-12-08 11:19:44Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_graph/graph_select.c b/source/blender/editors/space_graph/graph_select.c index 7746f49d135..9aaef9fca8a 100644 --- a/source/blender/editors/space_graph/graph_select.c +++ b/source/blender/editors/space_graph/graph_select.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: editaction.c 17746 2008-12-08 11:19:44Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_image/Makefile b/source/blender/editors/space_image/Makefile index e7e9a9b5665..44d841a0606 100644 --- a/source/blender/editors/space_image/Makefile +++ b/source/blender/editors/space_image/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_image/image_buttons.c b/source/blender/editors/space_image/image_buttons.c index a08a23c1263..b5df0257e71 100644 --- a/source/blender/editors/space_image/image_buttons.c +++ b/source/blender/editors/space_image/image_buttons.c @@ -383,7 +383,6 @@ static void image_editcursor_buts(const bContext *C, View2D *v2d, uiBlock *block } } -#if 0 static void image_panel_view_properties(const bContext *C, Panel *pa) { SpaceImage *sima= (SpaceImage*)CTX_wm_space_data(C); @@ -440,7 +439,6 @@ static void image_panel_view_properties(const bContext *C, Panel *pa) } image_editcursor_buts(C, &ar->v2d, block); } -#endif void brush_buttons(const bContext *C, uiBlock *block, short fromsima, int evt_nop, int evt_change, @@ -1025,53 +1023,42 @@ static void image_load_fs_cb(bContext *C, void *ima_pp_v, void *iuser_v) static void image_multi_cb(bContext *C, void *rr_v, void *iuser_v) { BKE_image_multilayer_index(rr_v, iuser_v); - WM_event_add_notifier(C, NC_IMAGE|ND_DRAW, NULL); } static void image_multi_inclay_cb(bContext *C, void *rr_v, void *iuser_v) { RenderResult *rr= rr_v; ImageUser *iuser= iuser_v; int tot= BLI_countlist(&rr->layers) + (rr->rectf?1:0); /* fake compo result layer */ - - if(iuser->layer<tot-1) { + if(iuser->layer<tot-1) iuser->layer++; - BKE_image_multilayer_index(rr, iuser); - WM_event_add_notifier(C, NC_IMAGE|ND_DRAW, NULL); - } + BKE_image_multilayer_index(rr, iuser); } static void image_multi_declay_cb(bContext *C, void *rr_v, void *iuser_v) { ImageUser *iuser= iuser_v; - - if(iuser->layer>0) { + if(iuser->layer>0) iuser->layer--; - BKE_image_multilayer_index(rr_v, iuser); - WM_event_add_notifier(C, NC_IMAGE|ND_DRAW, NULL); - } + BKE_image_multilayer_index(rr_v, iuser); } static void image_multi_incpass_cb(bContext *C, void *rr_v, void *iuser_v) { RenderResult *rr= rr_v; ImageUser *iuser= iuser_v; RenderLayer *rl= BLI_findlink(&rr->layers, iuser->layer); - if(rl) { int tot= BLI_countlist(&rl->passes) + (rl->rectf?1:0); /* builtin render result has no combined pass in list */ if(iuser->pass<tot-1) { iuser->pass++; BKE_image_multilayer_index(rr, iuser); - WM_event_add_notifier(C, NC_IMAGE|ND_DRAW, NULL); } } } static void image_multi_decpass_cb(bContext *C, void *rr_v, void *iuser_v) { ImageUser *iuser= iuser_v; - if(iuser->pass>0) { iuser->pass--; BKE_image_multilayer_index(rr_v, iuser); - WM_event_add_notifier(C, NC_IMAGE|ND_DRAW, NULL); } } @@ -1366,23 +1353,6 @@ void ED_image_uiblock_panel(const bContext *C, uiBlock *block, Image **ima_pp, I uiBlockEndAlign(block); } -void uiTemplateImageLayers(uiLayout *layout, bContext *C, Image *ima, ImageUser *iuser) -{ - uiBlock *block= uiLayoutFreeBlock(layout); - Scene *scene= CTX_data_scene(C); - RenderResult *rr; - - /* render layers and passes */ - if(ima && iuser) { - rr= BKE_image_get_renderresult(scene, ima); - - if(rr) { - uiBlockBeginAlign(block); - uiblock_layer_pass_buttons(block, rr, iuser, 0, 0, 0, 160); - uiBlockEndAlign(block); - } - } -} static void image_panel_properties(const bContext *C, Panel *pa) { @@ -1407,6 +1377,12 @@ void image_buttons_register(ARegionType *art) pt->draw= image_panel_properties; BLI_addtail(&art->paneltypes, pt); + pt= MEM_callocN(sizeof(PanelType), "spacetype image view properties"); + strcpy(pt->idname, "IMAGE_PT_view_properties"); + strcpy(pt->label, "View Properties"); + pt->draw= image_panel_view_properties; + BLI_addtail(&art->paneltypes, pt); + pt= MEM_callocN(sizeof(PanelType), "spacetype image panel paint"); strcpy(pt->idname, "IMAGE_PT_paint"); strcpy(pt->label, "Paint"); diff --git a/source/blender/editors/space_image/image_draw.c b/source/blender/editors/space_image/image_draw.c index e61931f2fad..122e298baaa 100644 --- a/source/blender/editors/space_image/image_draw.c +++ b/source/blender/editors/space_image/image_draw.c @@ -311,14 +311,12 @@ static void sima_draw_alpha_pixelsf(float x1, float y1, int rectx, int recty, fl // glColorMask(1, 1, 1, 1); } -#ifdef WITH_LCMS static void sima_draw_colorcorrected_pixels(float x1, float y1, ImBuf *ibuf) { colorcorrection_do_ibuf(ibuf, "MONOSCNR.ICM"); /* path is hardcoded here, find some place better */ glaDrawPixelsSafe(x1, y1, ibuf->x, ibuf->y, ibuf->x, GL_RGBA, GL_UNSIGNED_BYTE, ibuf->crect); } -#endif static void sima_draw_zbuf_pixels(float x1, float y1, int rectx, int recty, int *recti) { @@ -452,7 +450,7 @@ static unsigned int *get_part_from_ibuf(ImBuf *ibuf, short startx, short starty, return rectmain; } -static void draw_image_buffer_tiled(SpaceImage *sima, ARegion *ar, Image *ima, ImBuf *ibuf, float fx, float fy, float zoomx, float zoomy) +static void draw_image_buffer_tiled(SpaceImage *sima, ARegion *ar, Image *ima, ImBuf *ibuf, float zoomx, float zoomy) { unsigned int *rect; int dx, dy, sx, sy, x, y; @@ -479,7 +477,7 @@ static void draw_image_buffer_tiled(SpaceImage *sima, ARegion *ar, Image *ima, I /* draw repeated */ for(sy=0; sy+dy<=ibuf->y; sy+= dy) { for(sx=0; sx+dx<=ibuf->x; sx+= dx) { - UI_view2d_to_region_no_clip(&ar->v2d, fx + (float)sx/(float)ibuf->x, fy + (float)sy/(float)ibuf->y, &x, &y); + UI_view2d_view_to_region(&ar->v2d, (float)sx/(float)ibuf->x, (float)sy/(float)ibuf->y, &x, &y); glaDrawPixelsSafe(x, y, dx, dy, dx, GL_RGBA, GL_UNSIGNED_BYTE, rect); } @@ -490,19 +488,16 @@ static void draw_image_buffer_tiled(SpaceImage *sima, ARegion *ar, Image *ima, I MEM_freeN(rect); } -static void draw_image_buffer_repeated(SpaceImage *sima, ARegion *ar, Scene *scene, Image *ima, ImBuf *ibuf, float zoomx, float zoomy) +static void draw_image_buffer_repeated(SpaceImage *sima, ARegion *ar, Scene *scene, ImBuf *ibuf, float zoomx, float zoomy) { float x, y; double time_current; time_current = PIL_check_seconds_timer(); - for(x=floor(ar->v2d.cur.xmin); x<ar->v2d.cur.xmax; x += 1.0f) { - for(y=floor(ar->v2d.cur.ymin); y<ar->v2d.cur.ymax; y += 1.0f) { - if(ima && (ima->tpageflag & IMA_TILES)) - draw_image_buffer_tiled(sima, ar, ima, ibuf, x, y, zoomx, zoomy); - else - draw_image_buffer(sima, ar, scene, ibuf, x, y, zoomx, zoomy); + for(x=ar->v2d.cur.xmin; x<ar->v2d.cur.xmax; x += zoomx) { + for(y=ar->v2d.cur.ymin; y<ar->v2d.cur.ymax; y += zoomy) { + draw_image_buffer(sima, ar, scene, ibuf, x, y, zoomx, zoomy); /* only draw until running out of time */ if((PIL_check_seconds_timer() - time_current) > 0.25) @@ -672,9 +667,9 @@ void draw_image_main(SpaceImage *sima, ARegion *ar, Scene *scene) if(ibuf==NULL) draw_image_grid(ar, zoomx, zoomy); else if(sima->flag & SI_DRAW_TILE) - draw_image_buffer_repeated(sima, ar, scene, ima, ibuf, zoomx, zoomy); + draw_image_buffer_repeated(sima, ar, scene, ibuf, zoomx, zoomy); else if(ima && (ima->tpageflag & IMA_TILES)) - draw_image_buffer_tiled(sima, ar, ima, ibuf, 0.0f, 0.0, zoomx, zoomy); + draw_image_buffer_tiled(sima, ar, ima, ibuf, zoomx, zoomy); else draw_image_buffer(sima, ar, scene, ibuf, 0.0f, 0.0f, zoomx, zoomy); @@ -704,5 +699,12 @@ void draw_image_main(SpaceImage *sima, ARegion *ar, Scene *scene) } } #endif + +#if 0 + /* it is important to end a view in a transform compatible with buttons */ + bwin_scalematrix(sa->win, sima->blockscale, sima->blockscale, sima->blockscale); + if(!(G.rendering && show_render)) + image_blockhandlers(sa); +#endif } diff --git a/source/blender/editors/space_image/image_header.c b/source/blender/editors/space_image/image_header.c index 9550c4c3a29..adf4772efde 100644 --- a/source/blender/editors/space_image/image_header.c +++ b/source/blender/editors/space_image/image_header.c @@ -802,11 +802,11 @@ void image_header_buttons(const bContext *C, ARegion *ar) uiBlockBeginAlign(block); uiDefIconButBitS(block, TOG, SCE_SELECT_VERTEX, B_REDR, ICON_VERTEXSEL, - xco,yco,XIC,YIC, &scene->toolsettings->selectmode, 1.0, 0.0, 0, 0, "Vertex select mode"); + xco,yco,XIC,YIC, &scene->selectmode, 1.0, 0.0, 0, 0, "Vertex select mode"); uiDefIconButBitS(block, TOG, SCE_SELECT_EDGE, B_REDR, ICON_EDGESEL, - xco+=XIC,yco,XIC,YIC, &scene->toolsettings->selectmode, 1.0, 0.0, 0, 0, "Edge select mode"); + xco+=XIC,yco,XIC,YIC, &scene->selectmode, 1.0, 0.0, 0, 0, "Edge select mode"); uiDefIconButBitS(block, TOG, SCE_SELECT_FACE, B_REDR, ICON_FACESEL, - xco+=XIC,yco,XIC,YIC, &scene->toolsettings->selectmode, 1.0, 0.0, 0, 0, "Face select mode"); + xco+=XIC,yco,XIC,YIC, &scene->selectmode, 1.0, 0.0, 0, 0, "Face select mode"); uiBlockEndAlign(block); } @@ -837,14 +837,14 @@ void image_header_buttons(const bContext *C, ARegion *ar) /* snap options, identical to options in 3d view header */ uiBlockBeginAlign(block); - if (scene->toolsettings->snap_flag & SCE_SNAP) { - uiDefIconButBitS(block, TOG, SCE_SNAP, B_REDR, ICON_SNAP_GEO,xco,yco,XIC,YIC, &scene->toolsettings->snap_flag, 0, 0, 0, 0, "Use Snap or Grid (Shift Tab)."); + if (scene->snap_flag & SCE_SNAP) { + uiDefIconButBitS(block, TOG, SCE_SNAP, B_REDR, ICON_SNAP_GEO,xco,yco,XIC,YIC, &scene->snap_flag, 0, 0, 0, 0, "Use Snap or Grid (Shift Tab)."); xco+= XIC; - uiDefButS(block, MENU, B_NOP, "Mode%t|Closest%x0|Center%x1|Median%x2",xco,yco,70,YIC, &scene->toolsettings->snap_target, 0, 0, 0, 0, "Snap Target Mode."); + uiDefButS(block, MENU, B_NOP, "Mode%t|Closest%x0|Center%x1|Median%x2",xco,yco,70,YIC, &scene->snap_target, 0, 0, 0, 0, "Snap Target Mode."); xco+= 70; } else { - uiDefIconButBitS(block, TOG, SCE_SNAP, B_REDR, ICON_SNAP_GEAR,xco,yco,XIC,YIC, &scene->toolsettings->snap_flag, 0, 0, 0, 0, "Snap while Ctrl is held during transform (Shift Tab)."); + uiDefIconButBitS(block, TOG, SCE_SNAP, B_REDR, ICON_SNAP_GEAR,xco,yco,XIC,YIC, &scene->snap_flag, 0, 0, 0, 0, "Snap while Ctrl is held during transform (Shift Tab)."); xco+= XIC; } diff --git a/source/blender/editors/space_image/image_ops.c b/source/blender/editors/space_image/image_ops.c index 8f9bb0d05fe..537996601b8 100644 --- a/source/blender/editors/space_image/image_ops.c +++ b/source/blender/editors/space_image/image_ops.c @@ -577,30 +577,34 @@ void IMAGE_OT_view_zoom_ratio(wmOperatorType *ot) /**************** load/replace/save callbacks ******************/ -/* XXX make dynamic */ -static const EnumPropertyItem image_file_type_items[] = { - {R_TARGA, "TARGA", 0, "Targa", ""}, - {R_RAWTGA, "TARGA RAW", 0, "Targa Raw", ""}, - {R_PNG, "PNG", 0, "PNG", ""}, - {R_BMP, "BMP", 0, "BMP", ""}, - {R_JPEG90, "JPEG", 0, "Jpeg", ""}, +static char *filesel_imagetype_string(Image *ima) +{ + char *strp, *str= MEM_callocN(15*32, "menu for filesel"); + + strp= str; + str += sprintf(str, "Save Image as: %%t|"); + str += sprintf(str, "Targa %%x%d|", R_TARGA); + str += sprintf(str, "Targa Raw %%x%d|", R_RAWTGA); + str += sprintf(str, "PNG %%x%d|", R_PNG); + str += sprintf(str, "BMP %%x%d|", R_BMP); + str += sprintf(str, "Jpeg %%x%d|", R_JPEG90); #ifdef WITH_OPENJPEG - {R_JP2, "JPEG_2000", 0, "Jpeg 2000", ""}, + str += sprintf(str, "Jpeg 2000 %%x%d|", R_JP2); #endif - {R_IRIS, "IRIS", 0, "Iris", ""}, - //if(G.have_libtiff) - {R_TIFF, "TIFF", 0, "Tiff", ""}, - {R_RADHDR, "RADIANCE_HDR", 0, "Radiance HDR", ""}, - {R_CINEON, "CINEON", 0, "Cineon", ""}, - {R_DPX, "DPX", 0, "DPX", ""}, + str += sprintf(str, "Iris %%x%d|", R_IRIS); + if(G.have_libtiff) + str += sprintf(str, "Tiff %%x%d|", R_TIFF); + str += sprintf(str, "Radiance HDR %%x%d|", R_RADHDR); + str += sprintf(str, "Cineon %%x%d|", R_CINEON); + str += sprintf(str, "DPX %%x%d|", R_DPX); #ifdef WITH_OPENEXR - {R_OPENEXR, "OPENEXR", 0, "OpenEXR", ""}, + str += sprintf(str, "OpenEXR %%x%d|", R_OPENEXR); /* saving sequences of multilayer won't work, they copy buffers */ - /*if(ima->source==IMA_SRC_SEQUENCE && ima->type==IMA_TYPE_MULTILAYER); - else*/ - {R_MULTILAYER, "MULTILAYER", 0, "MultiLayer", ""}, + if(ima->source==IMA_SRC_SEQUENCE && ima->type==IMA_TYPE_MULTILAYER); + else str += sprintf(str, "MultiLayer %%x%d|", R_MULTILAYER); #endif - {0, NULL, 0, NULL, NULL}}; + return strp; +} static void image_filesel(bContext *C, wmOperator *op, const char *path) { @@ -795,9 +799,7 @@ static int save_as_exec(bContext *C, wmOperator *op) if(!ima) return OPERATOR_CANCELLED; - sima->imtypenr= RNA_enum_get(op->ptr, "file_type"); RNA_string_get(op->ptr, "filename", str); - save_image_doit(C, sima, scene, op, str); return OPERATOR_FINISHED; @@ -818,6 +820,10 @@ static int save_as_invoke(bContext *C, wmOperator *op, wmEvent *event) /* always opens fileselect */ if(ibuf) { + char *strp; + + strp= filesel_imagetype_string(ima); // XXX unused still + /* cant save multilayer sequence, ima->rr isn't valid for a specific frame */ if(ima->rr && !(ima->source==IMA_SRC_SEQUENCE && ima->type==IMA_TYPE_MULTILAYER)) sima->imtypenr= R_MULTILAYER; @@ -825,14 +831,14 @@ static int save_as_invoke(bContext *C, wmOperator *op, wmEvent *event) sima->imtypenr= scene->r.imtype; else sima->imtypenr= BKE_ftype_to_imtype(ibuf->ftype); - - RNA_enum_set(op->ptr, "file_type", sima->imtypenr); if(ibuf->name[0]==0) BLI_strncpy(ibuf->name, G.ima, FILE_MAX); // XXX note: we can give default menu enums to operator for this image_filesel(C, op, ibuf->name); + + MEM_freeN(strp); return OPERATOR_RUNNING_MODAL; } @@ -856,7 +862,6 @@ void IMAGE_OT_save_as(wmOperatorType *ot) /* properties */ RNA_def_string_file_path(ot->srna, "filename", "", FILE_MAX, "Filename", "File path to save image to."); - RNA_def_enum(ot->srna, "file_type", image_file_type_items, R_PNG, "File Type", "File type to save image as."); } /******************** save image operator ********************/ diff --git a/source/blender/editors/space_image/space_image.c b/source/blender/editors/space_image/space_image.c index 7d6faa00dfc..49f950fe67b 100644 --- a/source/blender/editors/space_image/space_image.c +++ b/source/blender/editors/space_image/space_image.c @@ -327,10 +327,12 @@ static void image_main_area_set_view2d(SpaceImage *sima, ARegion *ar, Scene *sce #endif if(sima->image) { ImBuf *ibuf= ED_space_image_buffer(sima); + float xuser_asp, yuser_asp; + ED_image_aspect(sima->image, &xuser_asp, &yuser_asp); if(ibuf) { - width= ibuf->x; - height= ibuf->y; + width= ibuf->x*xuser_asp; + height= ibuf->y*yuser_asp; } else if(sima->image->type==IMA_TYPE_R_RESULT) { /* not very important, just nice */ @@ -681,7 +683,7 @@ void ED_image_aspect(Image *ima, float *aspx, float *aspy) *aspx= *aspy= 1.0; if((ima == NULL) || (ima->type == IMA_TYPE_R_RESULT) || (ima->type == IMA_TYPE_COMPOSITE) || - (ima->aspx==0.0 || ima->aspy==0.0)) + (ima->tpageflag & IMA_TILES) || (ima->aspx==0.0 || ima->aspy==0.0)) return; /* x is always 1 */ diff --git a/source/blender/editors/space_info/Makefile b/source/blender/editors/space_info/Makefile index 931c2f2097c..bc04ddc7824 100644 --- a/source/blender/editors/space_info/Makefile +++ b/source/blender/editors/space_info/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_info/SConscript b/source/blender/editors/space_info/SConscript index 01268115687..05afcae162e 100644 --- a/source/blender/editors/space_info/SConscript +++ b/source/blender/editors/space_info/SConscript @@ -11,4 +11,7 @@ defs = [] if env['WITH_BF_GAMEENGINE']: defs.append('GAMEBLENDER=1') + if env['WITH_BF_SOLID']: + defs.append('USE_SUMO_SOLID') + env.BlenderLib ( 'bf_editors_space_info', sources, Split(incs), defs, libtype=['core'], priority=[70] ) diff --git a/source/blender/editors/space_info/info_header.c b/source/blender/editors/space_info/info_header.c index 7d6e2ca05c0..ac39c67d8f2 100644 --- a/source/blender/editors/space_info/info_header.c +++ b/source/blender/editors/space_info/info_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: info_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -415,7 +415,7 @@ static void operator_search_cb(const struct bContext *C, void *arg, char *str, u name[len]= '|'; } - if(0==uiSearchItemAdd(items, name, ot, 0)) + if(0==uiSearchItemAdd(items, name, ot)) break; } } @@ -491,7 +491,7 @@ void info_header_buttons(const bContext *C, ARegion *ar) static char search[256]= ""; uiBut *but= uiDefSearchBut(block, search, 0, ICON_VIEWZOOM, 256, xco+5, yco, 120, 19, ""); - uiButSetSearchFunc(but, operator_search_cb, NULL, operator_call_cb, NULL); + uiButSetSearchFunc(but, operator_search_cb, NULL, operator_call_cb); xco+= 125; } diff --git a/source/blender/editors/space_logic/Makefile b/source/blender/editors/space_logic/Makefile index d5709993368..e07a5bbf4a9 100644 --- a/source/blender/editors/space_logic/Makefile +++ b/source/blender/editors/space_logic/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_logic/SConscript b/source/blender/editors/space_logic/SConscript index e32fcc1b535..46a9858a836 100644 --- a/source/blender/editors/space_logic/SConscript +++ b/source/blender/editors/space_logic/SConscript @@ -12,4 +12,7 @@ defs = [] if env['WITH_BF_GAMEENGINE']: defs.append('GAMEBLENDER=1') + if env['WITH_BF_SOLID']: + defs.append('USE_SUMO_SOLID') + env.BlenderLib ( 'bf_editors_space_game', sources, Split(incs), defs, libtype=['core'], priority=[120] ) diff --git a/source/blender/editors/space_logic/logic_buttons.c b/source/blender/editors/space_logic/logic_buttons.c index b082d5d6ae2..240ddfc2614 100644 --- a/source/blender/editors/space_logic/logic_buttons.c +++ b/source/blender/editors/space_logic/logic_buttons.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: image_buttons.c 20913 2009-06-16 01:22:56Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_logic/logic_header.c b/source/blender/editors/space_logic/logic_header.c index d0e905728be..00fc130e771 100644 --- a/source/blender/editors/space_logic/logic_header.c +++ b/source/blender/editors/space_logic/logic_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: logic_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_logic/logic_window.c b/source/blender/editors/space_logic/logic_window.c index 55e21561c34..b9385a54d34 100644 --- a/source/blender/editors/space_logic/logic_window.c +++ b/source/blender/editors/space_logic/logic_window.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: logic_window.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -3056,12 +3056,12 @@ void logic_buttons(bContext *C, ARegion *ar) /* ******************************* */ xco= 500; yco= 170; width= 300; - uiDefBlockBut(block, controller_menu, NULL, "Controllers", xco-10, yco+35, 100, UI_UNIT_Y, ""); + uiDefPulldownBut(block, controller_menu, NULL, "Controllers", xco-10, yco+35, 100, 19, ""); uiBlockBeginAlign(block); - uiDefButBitS(block, TOG, BUTS_CONT_SEL, B_REDR, "Sel", xco+110, yco+35, (width-100)/3, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show all selected Objects"); - uiDefButBitS(block, TOG, BUTS_CONT_ACT, B_REDR, "Act", xco+110+(width-100)/3, yco+35, (width-100)/3, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show active Object"); - uiDefButBitS(block, TOG, BUTS_CONT_LINK, B_REDR, "Link", xco+110+2*(width-100)/3, yco+35, (width-100)/3, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show linked Objects to Sensor/Actuator"); + uiDefButBitS(block, TOG, BUTS_CONT_SEL, B_REDR, "Sel", xco+110, yco+35, (width-100)/3, 19, &slogic->scaflag, 0, 0, 0, 0, "Show all selected Objects"); + uiDefButBitS(block, TOG, BUTS_CONT_ACT, B_REDR, "Act", xco+110+(width-100)/3, yco+35, (width-100)/3, 19, &slogic->scaflag, 0, 0, 0, 0, "Show active Object"); + uiDefButBitS(block, TOG, BUTS_CONT_LINK, B_REDR, "Link", xco+110+2*(width-100)/3, yco+35, (width-100)/3, 19, &slogic->scaflag, 0, 0, 0, 0, "Show linked Objects to Sensor/Actuator"); uiBlockEndAlign(block); ob= CTX_data_active_object(C); @@ -3077,9 +3077,9 @@ void logic_buttons(bContext *C, ARegion *ar) /* presume it is only objects for now */ uiBlockBeginAlign(block); // if(ob->controllers.first) uiSetCurFont(block, UI_HELVB); - uiDefButBitS(block, TOG, OB_SHOWCONT, B_REDR, ob->id.name+2,(short)(xco-10), yco, (short)(width-30), UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Active Object name"); + uiDefButBitS(block, TOG, OB_SHOWCONT, B_REDR, ob->id.name+2,(short)(xco-10), yco, (short)(width-30), 19, &ob->scaflag, 0, 0, 0, 0, "Active Object name"); // if(ob->controllers.first) uiSetCurFont(block, UI_HELV); - uiDefButBitS(block, TOG, OB_ADDCONT, B_ADD_CONT, "Add",(short)(xco+width-40), yco, 50, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Add a new Controller"); + uiDefButBitS(block, TOG, OB_ADDCONT, B_ADD_CONT, "Add",(short)(xco+width-40), yco, 50, 19, &ob->scaflag, 0, 0, 0, 0, "Add a new Controller"); uiBlockEndAlign(block); yco-=20; @@ -3100,7 +3100,7 @@ void logic_buttons(bContext *C, ARegion *ar) if(ob->scaflag & OB_SHOWCONT) { /* first show the state */ - uiDefBlockBut(block, object_state_mask_menu, ob, "State", (short)(xco-10), (short)(yco-10), 36, UI_UNIT_Y, "Object state menu: store and retrieve initial state"); + uiDefBlockBut(block, object_state_mask_menu, ob, "State", (short)(xco-10), (short)(yco-10), 36, 19, "Object state menu: store and retrieve initial state"); if (!ob->state) ob->state = 1; @@ -3116,9 +3116,9 @@ void logic_buttons(bContext *C, ARegion *ar) } } uiBlockBeginAlign(block); - uiDefButBitS(block, TOG, OB_SETSTBIT, B_SET_STATE_BIT, "All",(short)(xco+226), yco-10, 22, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Set all state bits"); - uiDefButBitS(block, TOG, OB_INITSTBIT, B_INIT_STATE_BIT, "Ini",(short)(xco+248), yco-10, 22, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Set the initial state"); - uiDefButBitS(block, TOG, OB_DEBUGSTATE, 0, "D",(short)(xco+270), yco-10, 15, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Print state debug info"); + uiDefButBitS(block, TOG, OB_SETSTBIT, B_SET_STATE_BIT, "All",(short)(xco+226), yco-10, 22, 19, &ob->scaflag, 0, 0, 0, 0, "Set all state bits"); + uiDefButBitS(block, TOG, OB_INITSTBIT, B_INIT_STATE_BIT, "Ini",(short)(xco+248), yco-10, 22, 19, &ob->scaflag, 0, 0, 0, 0, "Set the initial state"); + uiDefButBitS(block, TOG, OB_DEBUGSTATE, 0, "D",(short)(xco+270), yco-10, 15, 19, &ob->scaflag, 0, 0, 0, 0, "Print state debug info"); uiBlockEndAlign(block); yco-=35; @@ -3142,17 +3142,17 @@ void logic_buttons(bContext *C, ARegion *ar) if (act) act->flag |= ACT_VISIBLE; } - uiDefIconButBitS(block, TOG, CONT_DEL, B_DEL_CONT, ICON_X, xco, yco, 22, UI_UNIT_Y, &cont->flag, 0, 0, 0, 0, "Delete Controller"); - uiDefIconButBitS(block, ICONTOG, CONT_SHOW, B_REDR, ICON_RIGHTARROW, (short)(xco+width-22), yco, 22, UI_UNIT_Y, &cont->flag, 0, 0, 0, 0, "Controller settings"); - uiDefIconButBitS(block, TOG, CONT_PRIO, B_REDR, ICON_BOOKMARKS, (short)(xco+width-66), yco, 22, UI_UNIT_Y, &cont->flag, 0, 0, 0, 0, "Mark controller for execution before all non-marked controllers (good for startup scripts)"); + uiDefIconButBitS(block, TOG, CONT_DEL, B_DEL_CONT, ICON_X, xco, yco, 22, 19, &cont->flag, 0, 0, 0, 0, "Delete Controller"); + uiDefIconButBitS(block, ICONTOG, CONT_SHOW, B_REDR, ICON_RIGHTARROW, (short)(xco+width-22), yco, 22, 19, &cont->flag, 0, 0, 0, 0, "Controller settings"); + uiDefIconButBitS(block, TOG, CONT_PRIO, B_REDR, ICON_BOOKMARKS, (short)(xco+width-66), yco, 22, 19, &cont->flag, 0, 0, 0, 0, "Mark controller for execution before all non-marked controllers (good for startup scripts)"); sprintf(name, "%d", first_bit(cont->state_mask)+1); - uiDefBlockBut(block, controller_state_mask_menu, cont, name, (short)(xco+width-44), yco, 22, UI_UNIT_Y, "Set controller state index (from 1 to 30)"); + uiDefBlockBut(block, controller_state_mask_menu, cont, name, (short)(xco+width-44), yco, 22, 19, "Set controller state index (from 1 to 30)"); if(cont->flag & CONT_SHOW) { cont->otype= cont->type; - uiDefButS(block, MENU, B_CHANGE_CONT, controller_pup(),(short)(xco+22), yco, 70, UI_UNIT_Y, &cont->type, 0, 0, 0, 0, "Controller type"); - but= uiDefBut(block, TEX, 1, "", (short)(xco+92), yco, (short)(width-158), UI_UNIT_Y, cont->name, 0, 31, 0, 0, "Controller name"); + uiDefButS(block, MENU, B_CHANGE_CONT, controller_pup(),(short)(xco+22), yco, 70, 19, &cont->type, 0, 0, 0, 0, "Controller type"); + but= uiDefBut(block, TEX, 1, "", (short)(xco+92), yco, (short)(width-158), 19, cont->name, 0, 31, 0, 0, "Controller name"); uiButSetFunc(but, make_unique_prop_names_cb, cont->name, (void*) 0); ycoo= yco; @@ -3162,17 +3162,17 @@ void logic_buttons(bContext *C, ARegion *ar) else { cpack(0x999999); glRecti(xco+22, yco, xco+width-22,yco+19); - but= uiDefBut(block, LABEL, 0, controller_name(cont->type), (short)(xco+22), yco, 70, UI_UNIT_Y, cont, 0, 0, 0, 0, "Controller type"); + but= uiDefBut(block, LABEL, 0, controller_name(cont->type), (short)(xco+22), yco, 70, 19, cont, 0, 0, 0, 0, "Controller type"); uiButSetFunc(but, sca_move_controller, cont, NULL); - but= uiDefBut(block, LABEL, 0, cont->name,(short)(xco+92), yco,(short)(width-158), UI_UNIT_Y, cont, 0, 0, 0, 0, "Controller name"); + but= uiDefBut(block, LABEL, 0, cont->name,(short)(xco+92), yco,(short)(width-158), 19, cont, 0, 0, 0, 0, "Controller name"); uiButSetFunc(but, sca_move_controller, cont, NULL); ycoo= yco; } - but= uiDefIconBut(block, LINK, 0, ICON_LINK, (short)(xco+width), ycoo, UI_UNIT_X, UI_UNIT_Y, NULL, 0, 0, 0, 0, ""); + but= uiDefIconBut(block, LINK, 0, ICON_LINK, (short)(xco+width), ycoo, 19, 19, NULL, 0, 0, 0, 0, ""); uiSetButLink(but, NULL, (void ***)&(cont->links), &cont->totlinks, LINK_CONTROLLER, LINK_ACTUATOR); - uiDefIconBut(block, INLINK, 0, ICON_INLINK,(short)(xco-19), ycoo, UI_UNIT_X, UI_UNIT_Y, cont, LINK_CONTROLLER, 0, 0, 0, ""); + uiDefIconBut(block, INLINK, 0, ICON_INLINK,(short)(xco-19), ycoo, 19, 19, cont, LINK_CONTROLLER, 0, 0, 0, ""); /* offset is >0 if at least one controller was displayed */ offset++; yco-=20; @@ -3188,13 +3188,13 @@ void logic_buttons(bContext *C, ARegion *ar) /* ******************************* */ xco= 10; yco= 170; width= 400; - uiDefBlockBut(block, sensor_menu, NULL, "Sensors", xco-10, yco+35, 70, UI_UNIT_Y, ""); + uiDefPulldownBut(block, sensor_menu, NULL, "Sensors", xco-10, yco+35, 70, 19, ""); uiBlockBeginAlign(block); - uiDefButBitS(block, TOG, BUTS_SENS_SEL, B_REDR, "Sel", xco+80, yco+35, (width-70)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show all selected Objects"); - uiDefButBitS(block, TOG, BUTS_SENS_ACT, B_REDR, "Act", xco+80+(width-70)/4, yco+35, (width-70)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show active Object"); - uiDefButBitS(block, TOG, BUTS_SENS_LINK, B_REDR, "Link", xco+80+2*(width-70)/4, yco+35, (width-70)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show linked Objects to Controller"); - uiDefButBitS(block, TOG, BUTS_SENS_STATE, B_REDR, "State", xco+80+3*(width-70)/4, yco+35, (width-70)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show only sensors connected to active states"); + uiDefButBitS(block, TOG, BUTS_SENS_SEL, B_REDR, "Sel", xco+80, yco+35, (width-70)/4, 19, &slogic->scaflag, 0, 0, 0, 0, "Show all selected Objects"); + uiDefButBitS(block, TOG, BUTS_SENS_ACT, B_REDR, "Act", xco+80+(width-70)/4, yco+35, (width-70)/4, 19, &slogic->scaflag, 0, 0, 0, 0, "Show active Object"); + uiDefButBitS(block, TOG, BUTS_SENS_LINK, B_REDR, "Link", xco+80+2*(width-70)/4, yco+35, (width-70)/4, 19, &slogic->scaflag, 0, 0, 0, 0, "Show linked Objects to Controller"); + uiDefButBitS(block, TOG, BUTS_SENS_STATE, B_REDR, "State", xco+80+3*(width-70)/4, yco+35, (width-70)/4, 19, &slogic->scaflag, 0, 0, 0, 0, "Show only sensors connected to active states"); uiBlockEndAlign(block); for(a=0; a<count; a++) { @@ -3207,9 +3207,9 @@ void logic_buttons(bContext *C, ARegion *ar) /* presume it is only objects for now */ uiBlockBeginAlign(block); // if(ob->sensors.first) uiSetCurFont(block, UI_HELVB); - uiDefButBitS(block, TOG, OB_SHOWSENS, B_REDR, ob->id.name+2,(short)(xco-10), yco, (short)(width-30), UI_UNIT_Y, &ob->scaflag, 0, 31, 0, 0, "Object name, click to show/hide sensors"); + uiDefButBitS(block, TOG, OB_SHOWSENS, B_REDR, ob->id.name+2,(short)(xco-10), yco, (short)(width-30), 19, &ob->scaflag, 0, 31, 0, 0, "Object name, click to show/hide sensors"); // if(ob->sensors.first) uiSetCurFont(block, UI_HELV); - uiDefButBitS(block, TOG, OB_ADDSENS, B_ADD_SENS, "Add",(short)(xco+width-40), yco, 50, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Add a new Sensor"); + uiDefButBitS(block, TOG, OB_ADDSENS, B_ADD_SENS, "Add",(short)(xco+width-40), yco, 50, 19, &ob->scaflag, 0, 0, 0, 0, "Add a new Sensor"); uiBlockEndAlign(block); yco-=20; @@ -3226,17 +3226,17 @@ void logic_buttons(bContext *C, ARegion *ar) pin = (slogic->scaflag & BUTS_SENS_STATE && (sens->flag & SENS_SHOW || sens->flag & SENS_PIN)) ? 1:0 ; sens->flag |= SENS_VISIBLE; - uiDefIconButBitS(block, TOG, SENS_DEL, B_DEL_SENS, ICON_X, xco, yco, 22, UI_UNIT_Y, &sens->flag, 0, 0, 0, 0, "Delete Sensor"); + uiDefIconButBitS(block, TOG, SENS_DEL, B_DEL_SENS, ICON_X, xco, yco, 22, 19, &sens->flag, 0, 0, 0, 0, "Delete Sensor"); if (pin) - uiDefIconButBitS(block, ICONTOG, SENS_PIN, B_REDR, ICON_PINNED, (short)(xco+width-44), yco, 22, UI_UNIT_Y, &sens->flag, 0, 0, 0, 0, "Display when not linked to a visible states controller"); + uiDefIconButBitS(block, ICONTOG, SENS_PIN, B_REDR, ICON_PINNED, (short)(xco+width-44), yco, 22, 19, &sens->flag, 0, 0, 0, 0, "Display when not linked to a visible states controller"); - uiDefIconButBitS(block, ICONTOG, SENS_SHOW, B_REDR, ICON_RIGHTARROW, (short)(xco+width-22), yco, 22, UI_UNIT_Y, &sens->flag, 0, 0, 0, 0, "Sensor settings"); + uiDefIconButBitS(block, ICONTOG, SENS_SHOW, B_REDR, ICON_RIGHTARROW, (short)(xco+width-22), yco, 22, 19, &sens->flag, 0, 0, 0, 0, "Sensor settings"); ycoo= yco; if(sens->flag & SENS_SHOW) { - uiDefButS(block, MENU, B_CHANGE_SENS, sensor_pup(), (short)(xco+22), yco, 80, UI_UNIT_Y, &sens->type, 0, 0, 0, 0, "Sensor type"); - but= uiDefBut(block, TEX, 1, "", (short)(xco+102), yco, (short)(width-(pin?146:124)), UI_UNIT_Y, sens->name, 0, 31, 0, 0, "Sensor name"); + uiDefButS(block, MENU, B_CHANGE_SENS, sensor_pup(), (short)(xco+22), yco, 80, 19, &sens->type, 0, 0, 0, 0, "Sensor type"); + but= uiDefBut(block, TEX, 1, "", (short)(xco+102), yco, (short)(width-(pin?146:124)), 19, sens->name, 0, 31, 0, 0, "Sensor name"); uiButSetFunc(but, make_unique_prop_names_cb, sens->name, (void*) 0); sens->otype= sens->type; @@ -3246,13 +3246,13 @@ void logic_buttons(bContext *C, ARegion *ar) else { set_col_sensor(sens->type, 1); glRecti(xco+22, yco, xco+width-22,yco+19); - but= uiDefBut(block, LABEL, 0, sensor_name(sens->type), (short)(xco+22), yco, 80, UI_UNIT_Y, sens, 0, 0, 0, 0, ""); + but= uiDefBut(block, LABEL, 0, sensor_name(sens->type), (short)(xco+22), yco, 80, 19, sens, 0, 0, 0, 0, ""); uiButSetFunc(but, sca_move_sensor, sens, NULL); - but= uiDefBut(block, LABEL, 0, sens->name, (short)(xco+102), yco, (short)(width-(pin?146:124)), UI_UNIT_Y, sens, 0, 31, 0, 0, ""); + but= uiDefBut(block, LABEL, 0, sens->name, (short)(xco+102), yco, (short)(width-(pin?146:124)), 19, sens, 0, 31, 0, 0, ""); uiButSetFunc(but, sca_move_sensor, sens, NULL); } - but= uiDefIconBut(block, LINK, 0, ICON_LINK, (short)(xco+width), ycoo, UI_UNIT_X, UI_UNIT_Y, NULL, 0, 0, 0, 0, ""); + but= uiDefIconBut(block, LINK, 0, ICON_LINK, (short)(xco+width), ycoo, 19, 19, NULL, 0, 0, 0, 0, ""); uiSetButLink(but, NULL, (void ***)&(sens->links), &sens->totlinks, LINK_SENSOR, LINK_CONTROLLER); yco-=20; @@ -3266,13 +3266,13 @@ void logic_buttons(bContext *C, ARegion *ar) /* ******************************* */ xco= 900; yco= 170; width= 400; - uiDefBlockBut(block, actuator_menu, NULL, "Actuators", xco-10, yco+35, 90, UI_UNIT_Y, ""); + uiDefPulldownBut(block, actuator_menu, NULL, "Actuators", xco-10, yco+35, 90, 19, ""); uiBlockBeginAlign(block); - uiDefButBitS(block, TOG, BUTS_ACT_SEL, B_REDR, "Sel", xco+110, yco+35, (width-100)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show all selected Objects"); - uiDefButBitS(block, TOG, BUTS_ACT_ACT, B_REDR, "Act", xco+110+(width-100)/4, yco+35, (width-100)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show active Object"); - uiDefButBitS(block, TOG, BUTS_ACT_LINK, B_REDR, "Link", xco+110+2*(width-100)/4, yco+35, (width-100)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show linked Objects to Controller"); - uiDefButBitS(block, TOG, BUTS_ACT_STATE, B_REDR, "State", xco+110+3*(width-100)/4, yco+35, (width-100)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show only actuators connected to active states"); + uiDefButBitS(block, TOG, BUTS_ACT_SEL, B_REDR, "Sel", xco+110, yco+35, (width-100)/4, 19, &slogic->scaflag, 0, 0, 0, 0, "Show all selected Objects"); + uiDefButBitS(block, TOG, BUTS_ACT_ACT, B_REDR, "Act", xco+110+(width-100)/4, yco+35, (width-100)/4, 19, &slogic->scaflag, 0, 0, 0, 0, "Show active Object"); + uiDefButBitS(block, TOG, BUTS_ACT_LINK, B_REDR, "Link", xco+110+2*(width-100)/4, yco+35, (width-100)/4, 19, &slogic->scaflag, 0, 0, 0, 0, "Show linked Objects to Controller"); + uiDefButBitS(block, TOG, BUTS_ACT_STATE, B_REDR, "State", xco+110+3*(width-100)/4, yco+35, (width-100)/4, 19, &slogic->scaflag, 0, 0, 0, 0, "Show only actuators connected to active states"); uiBlockEndAlign(block); for(a=0; a<count; a++) { ob= (Object *)idar[a]; @@ -3283,9 +3283,9 @@ void logic_buttons(bContext *C, ARegion *ar) /* presume it is only objects for now */ uiBlockBeginAlign(block); // if(ob->actuators.first) uiSetCurFont(block, UI_HELVB); - uiDefButBitS(block, TOG, OB_SHOWACT, B_REDR, ob->id.name+2,(short)(xco-10), yco,(short)(width-30), UI_UNIT_Y, &ob->scaflag, 0, 31, 0, 0, "Object name, click to show/hide actuators"); + uiDefButBitS(block, TOG, OB_SHOWACT, B_REDR, ob->id.name+2,(short)(xco-10), yco,(short)(width-30), 19, &ob->scaflag, 0, 31, 0, 0, "Object name, click to show/hide actuators"); // if(ob->actuators.first) uiSetCurFont(block, UI_HELV); - uiDefButBitS(block, TOG, OB_ADDACT, B_ADD_ACT, "Add",(short)(xco+width-40), yco, 50, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Add a new Actuator"); + uiDefButBitS(block, TOG, OB_ADDACT, B_ADD_ACT, "Add",(short)(xco+width-40), yco, 50, 19, &ob->scaflag, 0, 0, 0, 0, "Add a new Actuator"); uiBlockEndAlign(block); yco-=20; @@ -3301,15 +3301,15 @@ void logic_buttons(bContext *C, ARegion *ar) pin = (slogic->scaflag & BUTS_ACT_STATE && (act->flag & SENS_SHOW || act->flag & SENS_PIN)) ? 1:0 ; act->flag |= ACT_VISIBLE; /* mark the actuator as visible to help implementing the up/down action */ - uiDefIconButBitS(block, TOG, ACT_DEL, B_DEL_ACT, ICON_X, xco, yco, 22, UI_UNIT_Y, &act->flag, 0, 0, 0, 0, "Delete Actuator"); + uiDefIconButBitS(block, TOG, ACT_DEL, B_DEL_ACT, ICON_X, xco, yco, 22, 19, &act->flag, 0, 0, 0, 0, "Delete Actuator"); if (pin) - uiDefIconButBitS(block, ICONTOG, ACT_PIN, B_REDR, ICON_PINNED, (short)(xco+width-44), yco, 22, UI_UNIT_Y, &act->flag, 0, 0, 0, 0, "Display when not linked to a visible states controller"); - uiDefIconButBitS(block, ICONTOG, ACT_SHOW, B_REDR, ICON_RIGHTARROW, (short)(xco+width-22), yco, 22, UI_UNIT_Y, &act->flag, 0, 0, 0, 0, "Display the actuator"); + uiDefIconButBitS(block, ICONTOG, ACT_PIN, B_REDR, ICON_PINNED, (short)(xco+width-44), yco, 22, 19, &act->flag, 0, 0, 0, 0, "Display when not linked to a visible states controller"); + uiDefIconButBitS(block, ICONTOG, ACT_SHOW, B_REDR, ICON_RIGHTARROW, (short)(xco+width-22), yco, 22, 19, &act->flag, 0, 0, 0, 0, "Display the actuator"); if(act->flag & ACT_SHOW) { act->otype= act->type; - uiDefButS(block, MENU, B_CHANGE_ACT, actuator_pup(ob), (short)(xco+22), yco, 90, UI_UNIT_Y, &act->type, 0, 0, 0, 0, "Actuator type"); - but= uiDefBut(block, TEX, 1, "", (short)(xco+112), yco, (short)(width-(pin?156:134)), UI_UNIT_Y, act->name, 0, 31, 0, 0, "Actuator name"); + uiDefButS(block, MENU, B_CHANGE_ACT, actuator_pup(ob), (short)(xco+22), yco, 90, 19, &act->type, 0, 0, 0, 0, "Actuator type"); + but= uiDefBut(block, TEX, 1, "", (short)(xco+112), yco, (short)(width-(pin?156:134)), 19, act->name, 0, 31, 0, 0, "Actuator name"); uiButSetFunc(but, make_unique_prop_names_cb, act->name, (void*) 0); ycoo= yco; @@ -3319,14 +3319,14 @@ void logic_buttons(bContext *C, ARegion *ar) else { set_col_actuator(act->type, 1); glRecti((short)(xco+22), yco, (short)(xco+width-22),(short)(yco+19)); - but= uiDefBut(block, LABEL, 0, actuator_name(act->type), (short)(xco+22), yco, 90, UI_UNIT_Y, act, 0, 0, 0, 0, "Actuator type"); + but= uiDefBut(block, LABEL, 0, actuator_name(act->type), (short)(xco+22), yco, 90, 19, act, 0, 0, 0, 0, "Actuator type"); uiButSetFunc(but, sca_move_actuator, act, NULL); - but= uiDefBut(block, LABEL, 0, act->name, (short)(xco+112), yco, (short)(width-(pin?156:134)), UI_UNIT_Y, act, 0, 0, 0, 0, "Actuator name"); + but= uiDefBut(block, LABEL, 0, act->name, (short)(xco+112), yco, (short)(width-(pin?156:134)), 19, act, 0, 0, 0, 0, "Actuator name"); uiButSetFunc(but, sca_move_actuator, act, NULL); ycoo= yco; } - uiDefIconBut(block, INLINK, 0, ICON_INLINK,(short)(xco-19), ycoo, UI_UNIT_X, UI_UNIT_Y, act, LINK_ACTUATOR, 0, 0, 0, ""); + uiDefIconBut(block, INLINK, 0, ICON_INLINK,(short)(xco-19), ycoo, 19, 19, act, LINK_ACTUATOR, 0, 0, 0, ""); yco-=20; } diff --git a/source/blender/editors/space_nla/Makefile b/source/blender/editors/space_nla/Makefile index d7c9477dc83..43f010e6adc 100644 --- a/source/blender/editors/space_nla/Makefile +++ b/source/blender/editors/space_nla/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_nla/nla_header.c b/source/blender/editors/space_nla/nla_header.c index 0f6b77da6f5..2366a888d3b 100644 --- a/source/blender/editors/space_nla/nla_header.c +++ b/source/blender/editors/space_nla/nla_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: nla_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_node/Makefile b/source/blender/editors/space_node/Makefile index 5bd6e95e28c..60f81255a74 100644 --- a/source/blender/editors/space_node/Makefile +++ b/source/blender/editors/space_node/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_node/node_draw.c b/source/blender/editors/space_node/node_draw.c index f2e2486075b..0670dd9e01f 100644 --- a/source/blender/editors/space_node/node_draw.c +++ b/source/blender/editors/space_node/node_draw.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: drawnode.c 17439 2008-11-13 09:57:11Z kakbarnf $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_node/node_header.c b/source/blender/editors/space_node/node_header.c index 8c48d4b54e1..1031ad213f4 100644 --- a/source/blender/editors/space_node/node_header.c +++ b/source/blender/editors/space_node/node_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: node_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_outliner/Makefile b/source/blender/editors/space_outliner/Makefile index 8d7cd017e0b..19d40a4a31e 100644 --- a/source/blender/editors/space_outliner/Makefile +++ b/source/blender/editors/space_outliner/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_outliner/outliner.c b/source/blender/editors/space_outliner/outliner.c index 8017b8437ff..16748af39d5 100644 --- a/source/blender/editors/space_outliner/outliner.c +++ b/source/blender/editors/space_outliner/outliner.c @@ -1031,7 +1031,7 @@ static TreeElement *outliner_add_element(SpaceOops *soops, ListBase *lb, void *i } else if(ELEM3(type, TSE_RNA_STRUCT, TSE_RNA_PROPERTY, TSE_RNA_ARRAY_ELEM)) { PointerRNA pptr, propptr, *ptr= (PointerRNA*)idv; - PropertyRNA *prop, *iterprop; + PropertyRNA *prop, *iterprop, *nameprop; PropertyType proptype; PropertySubType propsubtype; int a, tot; @@ -1043,10 +1043,12 @@ static TreeElement *outliner_add_element(SpaceOops *soops, ListBase *lb, void *i } else if(type == TSE_RNA_STRUCT) { /* struct */ - te->name= RNA_struct_name_get_alloc(ptr, NULL, 0); + nameprop= RNA_struct_name_property(ptr->type); - if(te->name) + if(nameprop) { + te->name= RNA_property_string_get_alloc(ptr, nameprop, NULL, 0); te->flag |= TE_FREE_NAME; + } else te->name= (char*)RNA_struct_ui_name(ptr->type); @@ -3073,7 +3075,7 @@ static void tree_element_to_path(SpaceOops *soops, TreeElement *te, TreeStoreEle TreeElement *tem, *temnext, *temsub; TreeStoreElem *tse, *tsenext; PointerRNA *ptr, *nextptr; - PropertyRNA *prop; + PropertyRNA *prop, *nameprop; char *newpath=NULL; /* optimise tricks: @@ -3117,16 +3119,17 @@ static void tree_element_to_path(SpaceOops *soops, TreeElement *te, TreeStoreEle newpath= RNA_path_append(*path, ptr, prop, 0, NULL); } else if(RNA_property_type(prop) == PROP_COLLECTION) { - char buf[128], *name; - temnext= (TreeElement*)(ld->next->data); tsenext= TREESTORE(temnext); nextptr= &temnext->rnaptr; - name= RNA_struct_name_get_alloc(nextptr, buf, sizeof(buf)); + nameprop= RNA_struct_name_property(nextptr->type); - if(name) { + if(nameprop) { /* if possible, use name as a key in the path */ + char buf[128], *name; + name= RNA_property_string_get_alloc(nextptr, nameprop, buf, sizeof(buf)); + newpath= RNA_path_append(*path, NULL, prop, 0, name); if(name != buf) diff --git a/source/blender/editors/space_outliner/outliner_header.c b/source/blender/editors/space_outliner/outliner_header.c index fe2f054899c..b630eb2acf3 100644 --- a/source/blender/editors/space_outliner/outliner_header.c +++ b/source/blender/editors/space_outliner/outliner_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: outliner_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_outliner/space_outliner.c b/source/blender/editors/space_outliner/space_outliner.c index 4ddb586beb4..cc7880fcae7 100644 --- a/source/blender/editors/space_outliner/space_outliner.c +++ b/source/blender/editors/space_outliner/space_outliner.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: space_outliner.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_script/Makefile b/source/blender/editors/space_script/Makefile index 3322cb61a7f..48e1cd8e861 100644 --- a/source/blender/editors/space_script/Makefile +++ b/source/blender/editors/space_script/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_script/script_header.c b/source/blender/editors/space_script/script_header.c index d9851df4185..548ed8d2331 100644 --- a/source/blender/editors/space_script/script_header.c +++ b/source/blender/editors/space_script/script_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: script_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_sequencer/Makefile b/source/blender/editors/space_sequencer/Makefile index 7be0bc9cfef..80699db4baa 100644 --- a/source/blender/editors/space_sequencer/Makefile +++ b/source/blender/editors/space_sequencer/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_sequencer/sequencer_buttons.c b/source/blender/editors/space_sequencer/sequencer_buttons.c index cc4f5cf5ce3..f127ab4b0cf 100644 --- a/source/blender/editors/space_sequencer/sequencer_buttons.c +++ b/source/blender/editors/space_sequencer/sequencer_buttons.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: sequencer_buttons.c 20279 2009-05-19 17:13:33Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_sound/Makefile b/source/blender/editors/space_sound/Makefile index a072684d543..4d375282223 100644 --- a/source/blender/editors/space_sound/Makefile +++ b/source/blender/editors/space_sound/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_sound/sound_header.c b/source/blender/editors/space_sound/sound_header.c index ae3410663c2..b674438210d 100644 --- a/source/blender/editors/space_sound/sound_header.c +++ b/source/blender/editors/space_sound/sound_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: sound_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_text/Makefile b/source/blender/editors/space_text/Makefile index 50871017085..33e12dc1abb 100644 --- a/source/blender/editors/space_text/Makefile +++ b/source/blender/editors/space_text/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_text/text_header.c b/source/blender/editors/space_text/text_header.c index c761587198f..1a3f998bb8a 100644 --- a/source/blender/editors/space_text/text_header.c +++ b/source/blender/editors/space_text/text_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: text_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -88,7 +88,6 @@ /* ************************ header area region *********************** */ #ifndef DISABLE_PYTHON -#if 0 static void do_text_template_scriptsmenu(bContext *C, void *arg, int event) { // XXX BPY_menu_do_python(PYMENU_SCRIPTTEMPLATE, event); @@ -155,7 +154,6 @@ static uiBlock *text_plugin_scriptsmenu(bContext *C, void *args_unused) return block; } #endif -#endif /************************** properties ******************************/ diff --git a/source/blender/editors/space_text/text_python.c b/source/blender/editors/space_text/text_python.c index 4fa54cdf27b..e4c697dc2b5 100644 --- a/source/blender/editors/space_text/text_python.c +++ b/source/blender/editors/space_text/text_python.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: text_python.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_time/Makefile b/source/blender/editors/space_time/Makefile index e0bf3943dd8..20877b48559 100644 --- a/source/blender/editors/space_time/Makefile +++ b/source/blender/editors/space_time/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_time/space_time.c b/source/blender/editors/space_time/space_time.c index c4ca4d8522f..67759bb1b46 100644 --- a/source/blender/editors/space_time/space_time.c +++ b/source/blender/editors/space_time/space_time.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: space_time.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/space_time/time_header.c b/source/blender/editors/space_time/time_header.c index 29f31671670..2b00459fc17 100644 --- a/source/blender/editors/space_time/time_header.c +++ b/source/blender/editors/space_time/time_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: time_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -567,12 +567,12 @@ void time_header_buttons(const bContext *C, ARegion *ar) uiBlockBeginAlign(block); uiDefIconButBitS(block, TOG, AUTOKEY_ON, B_REDRAWALL, ICON_REC, - xco, yco, XIC, YIC, &(scene->toolsettings->autokey_mode), 0, 0, 0, 0, "Automatic keyframe insertion for Objects and Bones"); + xco, yco, XIC, YIC, &(scene->autokey_mode), 0, 0, 0, 0, "Automatic keyframe insertion for Objects and Bones"); xco+= XIC; if (IS_AUTOKEY_ON(scene)) { uiDefButS(block, MENU, B_REDRAWALL, "Auto-Keying Mode %t|Add/Replace Keys%x3|Replace Keys %x5", - xco, yco, (int)5.5*XIC, YIC, &(scene->toolsettings->autokey_mode), 0, 1, 0, 0, + xco, yco, (int)5.5*XIC, YIC, &(scene->autokey_mode), 0, 1, 0, 0, "Mode of automatic keyframe insertion for Objects and Bones"); xco+= (6*XIC); } diff --git a/source/blender/editors/space_view3d/Makefile b/source/blender/editors/space_view3d/Makefile index 5e6f8a6c426..dd4eab89411 100644 --- a/source/blender/editors/space_view3d/Makefile +++ b/source/blender/editors/space_view3d/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/space_view3d/drawobject.c b/source/blender/editors/space_view3d/drawobject.c index 05490e2fce1..a67e8c8a1c3 100644 --- a/source/blender/editors/space_view3d/drawobject.c +++ b/source/blender/editors/space_view3d/drawobject.c @@ -117,7 +117,7 @@ (vd->drawtype==OB_SOLID && vd->flag2 & V3D_SOLID_TEX)) #define CHECK_OB_DRAWFACEDOT(sce, vd, dt) \ -( (sce->toolsettings->selectmode & SCE_SELECT_FACE) && \ +( (sce->selectmode & SCE_SELECT_FACE) && \ (vd->drawtype<=OB_SOLID) && \ (((vd->drawtype==OB_SOLID) && (dt>=OB_SOLID) && (vd->flag2 & V3D_SOLID_TEX) && (vd->flag & V3D_ZBUF_SELECT)) == 0) \ ) @@ -1493,14 +1493,14 @@ void nurbs_foreachScreenVert(ViewContext *vc, void (*func)(void *userData, Nurb static void draw_dm_face_normals__mapFunc(void *userData, int index, float *cent, float *no) { - ToolSettings *ts= ((Scene *)userData)->toolsettings; + Scene *scene= (Scene *)userData; EditFace *efa = EM_get_face_for_index(index); if (efa->h==0 && efa->fgonf!=EM_FGON) { glVertex3fv(cent); - glVertex3f( cent[0] + no[0]*ts->normalsize, - cent[1] + no[1]*ts->normalsize, - cent[2] + no[2]*ts->normalsize); + glVertex3f( cent[0] + no[0]*scene->editbutsize, + cent[1] + no[1]*scene->editbutsize, + cent[2] + no[2]*scene->editbutsize); } } static void draw_dm_face_normals(Scene *scene, DerivedMesh *dm) @@ -1529,20 +1529,19 @@ static void draw_dm_face_centers(DerivedMesh *dm, int sel) static void draw_dm_vert_normals__mapFunc(void *userData, int index, float *co, float *no_f, short *no_s) { Scene *scene= (Scene *)userData; - ToolSettings *ts= scene->toolsettings; EditVert *eve = EM_get_vert_for_index(index); if (eve->h==0) { glVertex3fv(co); if (no_f) { - glVertex3f( co[0] + no_f[0]*ts->normalsize, - co[1] + no_f[1]*ts->normalsize, - co[2] + no_f[2]*ts->normalsize); + glVertex3f( co[0] + no_f[0]*scene->editbutsize, + co[1] + no_f[1]*scene->editbutsize, + co[2] + no_f[2]*scene->editbutsize); } else { - glVertex3f( co[0] + no_s[0]*ts->normalsize/32767.0f, - co[1] + no_s[1]*ts->normalsize/32767.0f, - co[2] + no_s[2]*ts->normalsize/32767.0f); + glVertex3f( co[0] + no_s[0]*scene->editbutsize/32767.0f, + co[1] + no_s[1]*scene->editbutsize/32767.0f, + co[2] + no_s[2]*scene->editbutsize/32767.0f); } } } @@ -1763,9 +1762,7 @@ static void draw_dm_bweights__mapFunc(void *userData, int index, float *co, floa } static void draw_dm_bweights(Scene *scene, DerivedMesh *dm) { - ToolSettings *ts= scene->toolsettings; - - if (ts->selectmode & SCE_SELECT_VERTEX) { + if (scene->selectmode & SCE_SELECT_VERTEX) { glPointSize(UI_GetThemeValuef(TH_VERTEX_SIZE) + 2); bglBegin(GL_POINTS); dm->foreachMappedVert(dm, draw_dm_bweights__mapFunc, NULL); @@ -1789,7 +1786,6 @@ static void draw_dm_bweights(Scene *scene, DerivedMesh *dm) static void draw_em_fancy_verts(Scene *scene, View3D *v3d, Object *obedit, EditMesh *em, DerivedMesh *cageDM, EditVert *eve_act) { - ToolSettings *ts= scene->toolsettings; int sel; if(v3d->zbuf) glDepthMask(0); // disable write in zbuffer, zbuf select @@ -1821,7 +1817,7 @@ static void draw_em_fancy_verts(Scene *scene, View3D *v3d, Object *obedit, EditM col[3] = fcol[3] = 255; } - if(ts->selectmode & SCE_SELECT_VERTEX) { + if(scene->selectmode & SCE_SELECT_VERTEX) { glPointSize(size); glColor4ubv((GLubyte *)col); draw_dm_verts(cageDM, sel, eve_act); @@ -1846,7 +1842,6 @@ static void draw_em_fancy_verts(Scene *scene, View3D *v3d, Object *obedit, EditM static void draw_em_fancy_edges(Scene *scene, View3D *v3d, Mesh *me, DerivedMesh *cageDM, short sel_only, EditEdge *eed_act) { - ToolSettings *ts= scene->toolsettings; int pass; unsigned char wireCol[4], selCol[4], actCol[4]; @@ -1876,11 +1871,11 @@ static void draw_em_fancy_edges(Scene *scene, View3D *v3d, Mesh *me, DerivedMesh if (!sel_only) wireCol[3] = 255; } - if(ts->selectmode == SCE_SELECT_FACE) { + if(scene->selectmode == SCE_SELECT_FACE) { draw_dm_edges_sel(cageDM, wireCol, selCol, actCol, eed_act); } - else if( (me->drawflag & ME_DRAWEDGES) || (ts->selectmode & SCE_SELECT_EDGE) ) { - if(cageDM->drawMappedEdgesInterp && (ts->selectmode & SCE_SELECT_VERTEX)) { + else if( (me->drawflag & ME_DRAWEDGES) || (scene->selectmode & SCE_SELECT_EDGE) ) { + if(cageDM->drawMappedEdgesInterp && (scene->selectmode & SCE_SELECT_VERTEX)) { glShadeModel(GL_SMOOTH); draw_dm_edges_sel_interp(cageDM, wireCol, selCol); glShadeModel(GL_FLAT); @@ -3244,9 +3239,6 @@ static void draw_new_particle_system(Scene *scene, View3D *v3d, RegionView3D *rv if(draw_as!=PART_DRAW_PATH){ state.time=cfra; if(psys_get_particle_state(scene,ob,psys,a,&state,0)){ - if(psys->parent) - Mat4MulVecfl(psys->parent->obmat, state.co); - /* create actiual particle data */ switch(draw_as){ case PART_DRAW_DOT: @@ -3669,13 +3661,13 @@ static void draw_particle_edit(Scene *scene, View3D *v3d, RegionView3D *rv3d, Ob } /* draw edit vertices */ - if(pset->selectmode!=SCE_SELECT_PATH){ + if(scene->selectmode!=SCE_SELECT_PATH){ glDisableClientState(GL_NORMAL_ARRAY); glEnableClientState(GL_COLOR_ARRAY); glDisable(GL_LIGHTING); glPointSize(UI_GetThemeValuef(TH_VERTEX_SIZE)); - if(pset->selectmode==SCE_SELECT_POINT){ + if(scene->selectmode==SCE_SELECT_POINT){ float *cd=0,*cdata=0; cd=cdata=MEM_callocN(edit->totkeys*(timed?4:3)*sizeof(float), "particle edit color data"); @@ -3714,7 +3706,7 @@ static void draw_particle_edit(Scene *scene, View3D *v3d, RegionView3D *rv3d, Ob MEM_freeN(cdata); cd=cdata=0; } - else if(pset->selectmode == SCE_SELECT_END){ + else if(scene->selectmode == SCE_SELECT_END){ for(i=0, pa=psys->particles; i<totpart; i++, pa++){ if((pa->flag & PARS_HIDE)==0){ key = edit->keys[i] + pa->totkey - 1; @@ -3952,7 +3944,6 @@ static void draw_editnurb(Object *ob, Nurb *nurb, int sel) static void drawnurb(Scene *scene, View3D *v3d, RegionView3D *rv3d, Base *base, Nurb *nurb, int dt) { - ToolSettings *ts= scene->toolsettings; Object *ob= base->object; Curve *cu = ob->data; Nurb *nu; @@ -3984,7 +3975,7 @@ static void drawnurb(Scene *scene, View3D *v3d, RegionView3D *rv3d, Base *base, /* direction vectors for 3d curve paths when at its lowest, dont render normals */ - if(cu->flag & CU_3D && ts->normalsize > 0.0015) { + if(cu->flag & CU_3D && scene->editbutsize > 0.0015) { UI_ThemeColor(TH_WIRE); for (bl=cu->bev.first,nu=nurb; nu && bl; bl=bl->next,nu=nu->next) { BevPoint *bevp= (BevPoint *)(bl+1); @@ -3992,7 +3983,7 @@ static void drawnurb(Scene *scene, View3D *v3d, RegionView3D *rv3d, Base *base, int skip= nu->resolu/16; while (nr-->0) { /* accounts for empty bevel lists */ - float fac= bevp->radius * ts->normalsize; + float fac= bevp->radius * scene->editbutsize; float ox,oy,oz; // Offset perpendicular to the curve float dx,dy,dz; // Delta along the curve @@ -5414,7 +5405,6 @@ static void bbs_mesh_solid(Scene *scene, View3D *v3d, Object *ob) void draw_object_backbufsel(Scene *scene, View3D *v3d, RegionView3D *rv3d, Object *ob) { - ToolSettings *ts= scene->toolsettings; wmMultMatrix(ob->obmat); @@ -5432,8 +5422,8 @@ void draw_object_backbufsel(Scene *scene, View3D *v3d, RegionView3D *rv3d, Objec EM_init_index_arrays(em, 1, 1, 1); - bbs_mesh_solid_EM(scene, v3d, ob, dm, ts->selectmode & SCE_SELECT_FACE); - if(ts->selectmode & SCE_SELECT_FACE) + bbs_mesh_solid_EM(scene, v3d, ob, dm, scene->selectmode & SCE_SELECT_FACE); + if(scene->selectmode & SCE_SELECT_FACE) em_solidoffs = 1+em->totface; else em_solidoffs= 1; @@ -5445,7 +5435,7 @@ void draw_object_backbufsel(Scene *scene, View3D *v3d, RegionView3D *rv3d, Objec em_wireoffs= em_solidoffs + em->totedge; // we draw verts if vert select mode or if in transform (for snap). - if(ts->selectmode & SCE_SELECT_VERTEX || G.moving & G_TRANSFORM_EDIT) { + if(scene->selectmode & SCE_SELECT_VERTEX || G.moving & G_TRANSFORM_EDIT) { bbs_mesh_verts(dm, em_wireoffs); em_vertoffs= em_wireoffs + em->totvert; } diff --git a/source/blender/editors/space_view3d/space_view3d.c b/source/blender/editors/space_view3d/space_view3d.c index 625b1838951..2d6a57d5a34 100644 --- a/source/blender/editors/space_view3d/space_view3d.c +++ b/source/blender/editors/space_view3d/space_view3d.c @@ -122,24 +122,6 @@ ARegion *view3d_has_tools_region(ScrArea *sa) return arnew; } -/* ****************************************************** */ - -/* function to always find a regionview3d context inside 3D window */ -RegionView3D *ED_view3d_context_rv3d(bContext *C) -{ - RegionView3D *rv3d= CTX_wm_region_view3d(C); - - if(rv3d==NULL) { - ScrArea *sa =CTX_wm_area(C); - if(sa->spacetype==SPACE_VIEW3D) { - ARegion *ar; - for(ar= sa->regionbase.first; ar; ar= ar->next) - if(ar->regiontype==RGN_TYPE_WINDOW) - return ar->regiondata; - } - } - return rv3d; -} /* ******************** default callbacks for view3d space ***************** */ diff --git a/source/blender/editors/space_view3d/view3d_buttons.c b/source/blender/editors/space_view3d/view3d_buttons.c index 91565235591..b6e9e05b120 100644 --- a/source/blender/editors/space_view3d/view3d_buttons.c +++ b/source/blender/editors/space_view3d/view3d_buttons.c @@ -1663,7 +1663,7 @@ static void view3d_panel_bonesketch_spaces(const bContext *C, Panel *pa) uiBlockEndAlign(block); - uiDefButBitS(block, TOG, SCE_SNAP_PEEL_OBJECT, B_NOP, "Peel Objects", 10, yco, 200, 20, &scene->toolsettings->snap_flag, 0, 0, 0, 0, "Peel whole objects as one"); + uiDefButBitS(block, TOG, SCE_SNAP_PEEL_OBJECT, B_NOP, "Peel Objects", 10, yco, 200, 20, &scene->snap_flag, 0, 0, 0, 0, "Peel whole objects as one"); } @@ -1710,7 +1710,7 @@ static void view3d_panel_operator_redo(const bContext *C, Panel *pa) } RNA_pointer_create(&wm->id, op->type->srna, op->properties, &ptr); - uiDefAutoButsRNA(C, pa->layout, &ptr, 2); + uiDefAutoButsRNA(C, pa->layout, &ptr); } void view3d_buttons_register(ARegionType *art) diff --git a/source/blender/editors/space_view3d/view3d_header.c b/source/blender/editors/space_view3d/view3d_header.c index 79ea90864f3..1c528aac6a3 100644 --- a/source/blender/editors/space_view3d/view3d_header.c +++ b/source/blender/editors/space_view3d/view3d_header.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: view3d_header.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -1812,7 +1812,6 @@ static void do_view3d_transformmenu(bContext *C, void *arg, int event) { #if 0 Scene *scene= CTX_data_scene(C); - ToolSettings *ts= CTX_data_tool_settings(C); switch(event) { case 1: @@ -1871,22 +1870,22 @@ static void do_view3d_transformmenu(bContext *C, void *arg, int event) Transform(); break; case 15: - ts->snap_flag &= ~SCE_SNAP; + scene->snap_flag &= ~SCE_SNAP; break; case 16: - ts->snap_flag |= SCE_SNAP; + scene->snap_flag |= SCE_SNAP; break; case 17: - ts->snap_target = SCE_SNAP_TARGET_CLOSEST; + scene->snap_target = SCE_SNAP_TARGET_CLOSEST; break; case 18: - ts->snap_target = SCE_SNAP_TARGET_CENTER; + scene->snap_target = SCE_SNAP_TARGET_CENTER; break; case 19: - ts->snap_target = SCE_SNAP_TARGET_MEDIAN; + scene->snap_target = SCE_SNAP_TARGET_MEDIAN; break; case 20: - ts->snap_target = SCE_SNAP_TARGET_ACTIVE; + scene->snap_target = SCE_SNAP_TARGET_ACTIVE; break; case 21: alignmenu(); @@ -1897,7 +1896,7 @@ static void do_view3d_transformmenu(bContext *C, void *arg, int event) static uiBlock *view3d_transformmenu(bContext *C, ARegion *ar, void *arg_unused) { - ToolSettings *ts= CTX_data_tool_settings(C); + Scene *scene= CTX_data_scene(C); Object *obedit = CTX_data_edit_object(C); uiBlock *block; short yco = 20, menuwidth = 120; @@ -1949,7 +1948,7 @@ static uiBlock *view3d_transformmenu(bContext *C, ARegion *ar, void *arg_unused) { uiDefBut(block, SEPR, 0, "", 0, yco-=6, menuwidth, 6, NULL, 0.0, 0.0, 0, 0, ""); - if (ts->snap_flag & SCE_SNAP) + if (scene->snap_flag & SCE_SNAP) { uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_DEHLT, "Grid", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 15, ""); uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Snap", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 16, ""); @@ -1962,7 +1961,7 @@ static uiBlock *view3d_transformmenu(bContext *C, ARegion *ar, void *arg_unused) uiDefBut(block, SEPR, 0, "", 0, yco-=6, menuwidth, 6, NULL, 0.0, 0.0, 0, 0, ""); - switch(ts->snap_target) + switch(scene->snap_target) { case SCE_SNAP_TARGET_CLOSEST: uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Snap Closest", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 17, ""); @@ -2651,34 +2650,34 @@ static uiBlock *view3d_edit_objectmenu(bContext *C, ARegion *ar, void *arg_unuse static void do_view3d_edit_propfalloffmenu(bContext *C, void *arg, int event) { - ToolSettings *ts= CTX_data_tool_settings(C); + Scene *scene= CTX_data_scene(C); - ts->prop_mode= event; + scene->prop_mode= event; } static uiBlock *view3d_edit_propfalloffmenu(bContext *C, ARegion *ar, void *arg_unused) { - ToolSettings *ts= CTX_data_tool_settings(C); + Scene *scene= CTX_data_scene(C); uiBlock *block; short yco = 20, menuwidth = 120; block= uiBeginBlock(C, ar, "view3d_edit_propfalloffmenu", UI_EMBOSSP); uiBlockSetButmFunc(block, do_view3d_edit_propfalloffmenu, NULL); - if (ts->prop_mode==PROP_SMOOTH) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Smooth|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_SMOOTH, ""); + if (scene->prop_mode==PROP_SMOOTH) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Smooth|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_SMOOTH, ""); else uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_DEHLT, "Smooth|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_SMOOTH, ""); - if (ts->prop_mode==PROP_SPHERE) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Sphere|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_SPHERE, ""); + if (scene->prop_mode==PROP_SPHERE) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Sphere|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_SPHERE, ""); else uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_DEHLT, "Sphere|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_SPHERE, ""); - if (ts->prop_mode==PROP_ROOT) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Root|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_ROOT, ""); + if (scene->prop_mode==PROP_ROOT) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Root|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_ROOT, ""); else uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_DEHLT, "Root|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_ROOT, ""); - if (ts->prop_mode==PROP_SHARP) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Sharp|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_SHARP, ""); + if (scene->prop_mode==PROP_SHARP) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Sharp|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_SHARP, ""); else uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_DEHLT, "Sharp|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_SHARP, ""); - if (ts->prop_mode==PROP_LIN) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Linear|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_LIN, ""); + if (scene->prop_mode==PROP_LIN) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Linear|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_LIN, ""); else uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_DEHLT, "Linear|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_LIN, ""); - if (ts->prop_mode==PROP_RANDOM) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Random|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_RANDOM, ""); + if (scene->prop_mode==PROP_RANDOM) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Random|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_RANDOM, ""); else uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_DEHLT, "Random|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_RANDOM, ""); - if (ts->prop_mode==PROP_CONST) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Constant|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_CONST, ""); + if (scene->prop_mode==PROP_CONST) uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Constant|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_CONST, ""); else uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_DEHLT, "Constant|Shift O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, PROP_CONST, ""); uiBlockSetDirection(block, UI_RIGHT); @@ -2699,7 +2698,7 @@ void do_view3d_edit_mesh_verticesmenu(bContext *C, void *arg, int event) make_parent(); break; case 1: /* remove doubles */ - count= removedoublesflag(1, 0, ts->doublimit); + count= removedoublesflag(1, 0, scene->toolsettings->doublimit); notice("Removed: %d", count); if (count) { /* only undo and redraw if an action is taken */ DAG_object_flush_update(scene, obedit, OB_RECALC_DATA); @@ -2769,18 +2768,18 @@ void do_view3d_edit_mesh_edgesmenu(bContext *C, void *arg, int event) switch(event) { case 0: /* subdivide smooth */ - esubdivideflag(1, 0.0, ts->editbutflag | B_SMOOTH,1,0); + esubdivideflag(1, 0.0, scene->toolsettings->editbutflag | B_SMOOTH,1,0); ED_undo_push(C, "Subdivide Smooth"); break; case 1: /*subdivide fractal */ randfac= 10; if(button(&randfac, 1, 100, "Rand fac:")==0) return; fac= -( (float)randfac )/100; - esubdivideflag(1, fac, ts->editbutflag,1,0); + esubdivideflag(1, fac, scene->toolsettings->editbutflag,1,0); ED_undo_push(C, "Subdivide Fractal"); break; case 2: /* subdivide */ - esubdivideflag(1, 0.0, ts->editbutflag,1,0); + esubdivideflag(1, 0.0, scene->toolsettings->editbutflag,1,0); ED_undo_push(C, "Subdivide"); break; case 3: /* knife subdivide */ @@ -3143,7 +3142,6 @@ static uiBlock *view3d_edit_mesh_scriptsmenu(bContext *C, ARegion *ar, void *arg static void do_view3d_edit_meshmenu(bContext *C, void *arg, int event) { #if 0 - ToolSettings *ts= CTX_data_tool_settings(C); Scene *scene= CTX_data_scene(C); ScrArea *sa= CTX_wm_area(C); View3D *v3d= sa->spacedata.first; @@ -3187,12 +3185,12 @@ static void do_view3d_edit_meshmenu(bContext *C, void *arg, int event) Transform(); break; case 12: /* proportional edit (toggle) */ - if(ts->proportional) ts->proportional= 0; - else ts->proportional= 1; + if(scene->proportional) scene->proportional= 0; + else scene->proportional= 1; break; case 13: /* automerge edit (toggle) */ - if(ts->automerge) ts->automerge= 0; - else ts->automerge= 1; + if(scene->automerge) scene->automerge= 0; + else scene->automerge= 1; break; case 15: uv_autocalc_tface(); @@ -3206,7 +3204,7 @@ static void do_view3d_edit_meshmenu(bContext *C, void *arg, int event) static uiBlock *view3d_edit_meshmenu(bContext *C, ARegion *ar, void *arg_unused) { - ToolSettings *ts= CTX_data_tool_settings(C); + Scene *scene= CTX_data_scene(C); Object *obedit = CTX_data_edit_object(C); uiBlock *block; short yco= 0, menuwidth=120; @@ -3252,7 +3250,7 @@ static uiBlock *view3d_edit_meshmenu(bContext *C, ARegion *ar, void *arg_unused) - if(ts->proportional) { + if(scene->proportional) { uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Proportional Editing|O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 12, ""); } else { uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_DEHLT, "Proportional Editing|O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 12, ""); @@ -3263,7 +3261,7 @@ static uiBlock *view3d_edit_meshmenu(bContext *C, ARegion *ar, void *arg_unused) /* PITA but we should let users know that automerge cant work with multires :/ */ uiDefIconTextBut(block, BUTM, 1, - ts->automerge ? ICON_CHECKBOX_HLT : ICON_CHECKBOX_DEHLT, + scene->automerge ? ICON_CHECKBOX_HLT : ICON_CHECKBOX_DEHLT, ((Mesh*)obedit->data)->mr ? "AutoMerge Editing (disabled by multires)" : "AutoMerge Editing", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 13, ""); @@ -3538,8 +3536,8 @@ static void do_view3d_edit_latticemenu(bContext *C, void *arg, int event) Transform(); break; case 5: /* proportional edit (toggle) */ - if(ts->proportional) ts->proportional= 0; - else ts->proportional= 1; + if(scene->proportional) scene->proportional= 0; + else scene->proportional= 1; break; case 7: /* delete keyframe */ common_deletekey(); @@ -3550,7 +3548,7 @@ static void do_view3d_edit_latticemenu(bContext *C, void *arg, int event) static uiBlock *view3d_edit_latticemenu(bContext *C, ARegion *ar, void *arg_unused) { - ToolSettings *ts= CTX_data_tool_settings(C); + Scene *scene= CTX_data_scene(C); uiBlock *block; short yco= 0, menuwidth=120; @@ -3576,7 +3574,7 @@ static uiBlock *view3d_edit_latticemenu(bContext *C, ARegion *ar, void *arg_unus uiDefBut(block, SEPR, 0, "", 0, yco-=6, menuwidth, 6, NULL, 0.0, 0.0, 0, 0, ""); - if(ts->proportional) { + if(scene->proportional) { uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_HLT, "Proportional Editing|O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 5, ""); } else { uiDefIconTextBut(block, BUTM, 1, ICON_CHECKBOX_DEHLT, "Proportional Editing|O", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 5, ""); @@ -4697,7 +4695,7 @@ static uiBlock *view3d_faceselmenu(bContext *C, ARegion *ar, void *arg_unused) static void view3d_select_particlemenu(bContext *C, uiLayout *layout, void *arg_unused) { - ToolSettings *ts= CTX_data_tool_settings(C); + Scene *scene= CTX_data_scene(C); uiItemO(layout, NULL, 0, "VIEW3D_OT_select_border"); @@ -4706,7 +4704,7 @@ static void view3d_select_particlemenu(bContext *C, uiLayout *layout, void *arg_ uiItemO(layout, NULL, 0, "PARTICLE_OT_select_all_toggle"); uiItemO(layout, NULL, 0, "PARTICLE_OT_select_linked"); - if(ts->particle.selectmode & SCE_SELECT_POINT) { + if(scene->selectmode & SCE_SELECT_POINT) { uiItemO(layout, NULL, 0, "PARTICLE_OT_select_last"); // |W, 4 uiItemO(layout, NULL, 0, "PARTICLE_OT_select_first"); // |W, 3 } @@ -4726,7 +4724,7 @@ static void view3d_particle_showhidemenu(bContext *C, uiLayout *layout, void *ar static void view3d_particlemenu(bContext *C, uiLayout *layout, void *arg_unused) { - ToolSettings *ts= CTX_data_tool_settings(C); + Scene *scene= CTX_data_scene(C); // XXX uiDefIconTextBut(block, BUTM, 1, ICON_MENU_PANEL, "Particle Edit Properties|N", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 0, 1, ""); // add_blockhandler(sa, VIEW3D_HANDLER_OBJECT, UI_PNL_UNSTOW); @@ -4741,7 +4739,7 @@ static void view3d_particlemenu(bContext *C, uiLayout *layout, void *arg_unused) uiItemO(layout, NULL, 0, "PARTICLE_OT_remove_doubles"); // |W, 5 uiItemO(layout, NULL, 0, "PARTICLE_OT_delete"); - if(ts->particle.selectmode & SCE_SELECT_POINT) + if(scene->selectmode & SCE_SELECT_POINT) uiItemO(layout, NULL, 0, "PARTICLE_OT_subdivide"); // |W, 2 uiItemO(layout, NULL, 0, "PARTICLE_OT_rekey"); // |W, 1 @@ -4875,7 +4873,6 @@ static void do_view3d_header_buttons(bContext *C, void *arg, int event) { wmWindow *win= CTX_wm_window(C); Scene *scene= CTX_data_scene(C); - ToolSettings *ts= CTX_data_tool_settings(C); ScrArea *sa= CTX_wm_area(C); View3D *v3d= sa->spacedata.first; Base *basact= CTX_data_active_base(C); @@ -5010,7 +5007,7 @@ static void do_view3d_header_buttons(bContext *C, void *arg, int event) if(em) { if(shift==0 || em->selectmode==0) em->selectmode= SCE_SELECT_VERTEX; - ts->selectmode= em->selectmode; + scene->selectmode= em->selectmode; EM_selectmode_set(em); WM_event_add_notifier(C, NC_OBJECT|ND_GEOM_SELECT, obedit); ED_undo_push(C, "Selectmode Set: Vertex"); @@ -5024,7 +5021,7 @@ static void do_view3d_header_buttons(bContext *C, void *arg, int event) } em->selectmode = SCE_SELECT_EDGE; } - ts->selectmode= em->selectmode; + scene->selectmode= em->selectmode; EM_selectmode_set(em); WM_event_add_notifier(C, NC_OBJECT|ND_GEOM_SELECT, obedit); ED_undo_push(C, "Selectmode Set: Edge"); @@ -5033,12 +5030,12 @@ static void do_view3d_header_buttons(bContext *C, void *arg, int event) case B_SEL_FACE: if(em) { if( shift==0 || em->selectmode==0){ - if( ((ts->selectmode ^ SCE_SELECT_FACE) == SCE_SELECT_VERTEX) || ((ts->selectmode ^ SCE_SELECT_FACE) == SCE_SELECT_EDGE)){ - if(ctrl) EM_convertsel(em, (ts->selectmode ^ SCE_SELECT_FACE),SCE_SELECT_FACE); + if( ((scene->selectmode ^ SCE_SELECT_FACE) == SCE_SELECT_VERTEX) || ((scene->selectmode ^ SCE_SELECT_FACE) == SCE_SELECT_EDGE)){ + if(ctrl) EM_convertsel(em, (scene->selectmode ^ SCE_SELECT_FACE),SCE_SELECT_FACE); } em->selectmode = SCE_SELECT_FACE; } - ts->selectmode= em->selectmode; + scene->selectmode= em->selectmode; EM_selectmode_set(em); WM_event_add_notifier(C, NC_OBJECT|ND_GEOM_SELECT, obedit); ED_undo_push(C, "Selectmode Set: Face"); @@ -5046,15 +5043,15 @@ static void do_view3d_header_buttons(bContext *C, void *arg, int event) break; case B_SEL_PATH: - ts->particle.selectmode= SCE_SELECT_PATH; + scene->selectmode= SCE_SELECT_PATH; ED_undo_push(C, "Selectmode Set: Path"); break; case B_SEL_POINT: - ts->particle.selectmode = SCE_SELECT_POINT; + scene->selectmode = SCE_SELECT_POINT; ED_undo_push(C, "Selectmode Set: Point"); break; case B_SEL_END: - ts->particle.selectmode = SCE_SELECT_END; + scene->selectmode = SCE_SELECT_END; ED_undo_push(C, "Selectmode Set: End point"); break; @@ -5283,7 +5280,6 @@ void view3d_header_buttons(const bContext *C, ARegion *ar) ScrArea *sa= CTX_wm_area(C); View3D *v3d= sa->spacedata.first; Scene *scene= CTX_data_scene(C); - ToolSettings *ts= CTX_data_tool_settings(C); Object *ob= OBACT; Object *obedit = CTX_data_edit_object(C); uiBlock *block; @@ -5453,11 +5449,11 @@ void view3d_header_buttons(const bContext *C, ARegion *ar) if((obedit && (obedit->type == OB_MESH || obedit->type == OB_CURVE || obedit->type == OB_SURF || obedit->type == OB_LATTICE)) || G.f & G_PARTICLEEDIT) { uiBlockBeginAlign(block); - uiDefIconTextButS(block, ICONTEXTROW,B_REDR, ICON_PROP_OFF, "Proportional %t|Off %x0|On %x1|Connected %x2", xco,yco,XIC+10,YIC, &(ts->proportional), 0, 1.0, 0, 0, "Proportional Edit Falloff (Hotkeys: O, Alt O) "); + uiDefIconTextButS(block, ICONTEXTROW,B_REDR, ICON_PROP_OFF, "Proportional %t|Off %x0|On %x1|Connected %x2", xco,yco,XIC+10,YIC, &(scene->proportional), 0, 1.0, 0, 0, "Proportional Edit Falloff (Hotkeys: O, Alt O) "); xco+= XIC+10; - if(ts->proportional) { - uiDefIconTextButS(block, ICONTEXTROW,B_REDR, ICON_SMOOTHCURVE, propfalloff_pup(), xco,yco,XIC+10,YIC, &(ts->prop_mode), 0.0, 0.0, 0, 0, "Proportional Edit Falloff (Hotkey: Shift O) "); + if(scene->proportional) { + uiDefIconTextButS(block, ICONTEXTROW,B_REDR, ICON_SMOOTHCURVE, propfalloff_pup(), xco,yco,XIC+10,YIC, &(scene->prop_mode), 0.0, 0.0, 0, 0, "Proportional Edit Falloff (Hotkey: Shift O) "); xco+= XIC+10; } uiBlockEndAlign(block); @@ -5468,21 +5464,21 @@ void view3d_header_buttons(const bContext *C, ARegion *ar) if (BIF_snappingSupported(obedit)) { uiBlockBeginAlign(block); - if (ts->snap_flag & SCE_SNAP) { - uiDefIconButBitS(block, TOG, SCE_SNAP, B_REDR, ICON_SNAP_GEO,xco,yco,XIC,YIC, &ts->snap_flag, 0, 0, 0, 0, "Snap while Ctrl is held during transform (Shift Tab)"); + if (scene->snap_flag & SCE_SNAP) { + uiDefIconButBitS(block, TOG, SCE_SNAP, B_REDR, ICON_SNAP_GEO,xco,yco,XIC,YIC, &scene->snap_flag, 0, 0, 0, 0, "Snap while Ctrl is held during transform (Shift Tab)"); xco+= XIC; - uiDefIconButBitS(block, TOG, SCE_SNAP_ROTATE, B_REDR, ICON_SNAP_NORMAL,xco,yco,XIC,YIC, &ts->snap_flag, 0, 0, 0, 0, "Align rotation with the snapping target"); + uiDefIconButBitS(block, TOG, SCE_SNAP_ROTATE, B_REDR, ICON_SNAP_NORMAL,xco,yco,XIC,YIC, &scene->snap_flag, 0, 0, 0, 0, "Align rotation with the snapping target"); xco+= XIC; - if (ts->snap_mode == SCE_SNAP_MODE_VOLUME) { - uiDefIconButBitS(block, TOG, SCE_SNAP_PEEL_OBJECT, B_REDR, ICON_SNAP_PEEL_OBJECT,xco,yco,XIC,YIC, &ts->snap_flag, 0, 0, 0, 0, "Consider objects as whole when finding volume center"); + if (scene->snap_mode == SCE_SNAP_MODE_VOLUME) { + uiDefIconButBitS(block, TOG, SCE_SNAP_PEEL_OBJECT, B_REDR, ICON_SNAP_PEEL_OBJECT,xco,yco,XIC,YIC, &scene->snap_flag, 0, 0, 0, 0, "Consider objects as whole when finding volume center"); xco+= XIC; } - uiDefIconTextButS(block, ICONTEXTROW,B_REDR, ICON_SNAP_VERTEX, snapmode_pup(), xco,yco,XIC+10,YIC, &(ts->snap_mode), 0.0, 0.0, 0, 0, "Snapping mode"); + uiDefIconTextButS(block, ICONTEXTROW,B_REDR, ICON_SNAP_VERTEX, snapmode_pup(), xco,yco,XIC+10,YIC, &(scene->snap_mode), 0.0, 0.0, 0, 0, "Snapping mode"); xco+= XIC; - uiDefButS(block, MENU, B_NOP, "Snap Mode%t|Closest%x0|Center%x1|Median%x2|Active%x3",xco,yco,70,YIC, &ts->snap_target, 0, 0, 0, 0, "Snap Target Mode"); + uiDefButS(block, MENU, B_NOP, "Snap Mode%t|Closest%x0|Center%x1|Median%x2|Active%x3",xco,yco,70,YIC, &scene->snap_target, 0, 0, 0, 0, "Snap Target Mode"); xco+= XIC+70; } else { - uiDefIconButBitS(block, TOG, SCE_SNAP, B_REDR, ICON_SNAP_GEAR,xco,yco,XIC,YIC, &ts->snap_flag, 0, 0, 0, 0, "Snap while Ctrl is held during transform (Shift Tab)"); + uiDefIconButBitS(block, TOG, SCE_SNAP, B_REDR, ICON_SNAP_GEAR,xco,yco,XIC,YIC, &scene->snap_flag, 0, 0, 0, 0, "Snap while Ctrl is held during transform (Shift Tab)"); xco+= XIC; } @@ -5513,11 +5509,11 @@ void view3d_header_buttons(const bContext *C, ARegion *ar) } else if(G.f & G_PARTICLEEDIT) { uiBlockBeginAlign(block); - uiDefIconButBitI(block, TOG, SCE_SELECT_PATH, B_SEL_PATH, ICON_EDGESEL, xco,yco,XIC,YIC, &ts->particle.selectmode, 1.0, 0.0, 0, 0, "Path edit mode"); + uiDefIconButBitS(block, TOG, SCE_SELECT_PATH, B_SEL_PATH, ICON_EDGESEL, xco,yco,XIC,YIC, &scene->selectmode, 1.0, 0.0, 0, 0, "Path edit mode"); xco+= XIC; - uiDefIconButBitI(block, TOG, SCE_SELECT_POINT, B_SEL_POINT, ICON_VERTEXSEL, xco,yco,XIC,YIC, &ts->particle.selectmode, 1.0, 0.0, 0, 0, "Point select mode"); + uiDefIconButBitS(block, TOG, SCE_SELECT_POINT, B_SEL_POINT, ICON_VERTEXSEL, xco,yco,XIC,YIC, &scene->selectmode, 1.0, 0.0, 0, 0, "Point select mode"); xco+= XIC; - uiDefIconButBitI(block, TOG, SCE_SELECT_END, B_SEL_END, ICON_FACESEL, xco,yco,XIC,YIC, &ts->particle.selectmode, 1.0, 0.0, 0, 0, "Tip select mode"); + uiDefIconButBitS(block, TOG, SCE_SELECT_END, B_SEL_END, ICON_FACESEL, xco,yco,XIC,YIC, &scene->selectmode, 1.0, 0.0, 0, 0, "Tip select mode"); xco+= XIC; uiBlockEndAlign(block); diff --git a/source/blender/editors/space_view3d/view3d_select.c b/source/blender/editors/space_view3d/view3d_select.c index a153f795292..e0e8ac7c7a7 100644 --- a/source/blender/editors/space_view3d/view3d_select.c +++ b/source/blender/editors/space_view3d/view3d_select.c @@ -438,7 +438,6 @@ static void do_lasso_select_mesh__doSelectFace(void *userData, EditFace *efa, in static void do_lasso_select_mesh(ViewContext *vc, short mcords[][2], short moves, short select) { struct { ViewContext vc; rcti *rect; short (*mcords)[2], moves, select, pass, done; } data; - ToolSettings *ts= vc->scene->toolsettings; rcti rect; int bbsel; @@ -457,14 +456,14 @@ static void do_lasso_select_mesh(ViewContext *vc, short mcords[][2], short moves bbsel= EM_mask_init_backbuf_border(vc, mcords, moves, rect.xmin, rect.ymin, rect.xmax, rect.ymax); - if(ts->selectmode & SCE_SELECT_VERTEX) { + if(vc->scene->selectmode & SCE_SELECT_VERTEX) { if (bbsel) { EM_backbuf_checkAndSelectVerts(vc->em, select); } else { mesh_foreachScreenVert(vc, do_lasso_select_mesh__doSelectVert, &data, 1); } } - if(ts->selectmode & SCE_SELECT_EDGE) { + if(vc->scene->selectmode & SCE_SELECT_EDGE) { /* Does both bbsel and non-bbsel versions (need screen cos for both) */ data.pass = 0; @@ -476,7 +475,7 @@ static void do_lasso_select_mesh(ViewContext *vc, short mcords[][2], short moves } } - if(ts->selectmode & SCE_SELECT_FACE) { + if(vc->scene->selectmode & SCE_SELECT_FACE) { if (bbsel) { EM_backbuf_checkAndSelectFaces(vc->em, select); } else { @@ -1278,7 +1277,6 @@ static void do_mesh_box_select__doSelectFace(void *userData, EditFace *efa, int static void do_mesh_box_select(ViewContext *vc, rcti *rect, int select) { struct { ViewContext vc; rcti *rect; short select, pass, done; } data; - ToolSettings *ts= vc->scene->toolsettings; int bbsel; data.vc= *vc; @@ -1289,14 +1287,14 @@ static void do_mesh_box_select(ViewContext *vc, rcti *rect, int select) bbsel= EM_init_backbuf_border(vc, rect->xmin, rect->ymin, rect->xmax, rect->ymax); - if(ts->selectmode & SCE_SELECT_VERTEX) { + if(vc->scene->selectmode & SCE_SELECT_VERTEX) { if (bbsel) { EM_backbuf_checkAndSelectVerts(vc->em, select); } else { mesh_foreachScreenVert(vc, do_mesh_box_select__doSelectVert, &data, 1); } } - if(ts->selectmode & SCE_SELECT_EDGE) { + if(vc->scene->selectmode & SCE_SELECT_EDGE) { /* Does both bbsel and non-bbsel versions (need screen cos for both) */ data.pass = 0; @@ -1308,7 +1306,7 @@ static void do_mesh_box_select(ViewContext *vc, rcti *rect, int select) } } - if(ts->selectmode & SCE_SELECT_FACE) { + if(vc->scene->selectmode & SCE_SELECT_FACE) { if(bbsel) { EM_backbuf_checkAndSelectFaces(vc->em, select); } else { @@ -1641,7 +1639,6 @@ static void mesh_circle_doSelectFace(void *userData, EditFace *efa, int x, int y static void mesh_circle_select(ViewContext *vc, int selecting, short *mval, float rad) { - ToolSettings *ts= vc->scene->toolsettings; int bbsel; if(vc->obedit==NULL && (FACESEL_PAINT_TEST)) { @@ -1669,7 +1666,7 @@ static void mesh_circle_select(ViewContext *vc, int selecting, short *mval, floa data.mval[1] = mval[1]; data.radius = rad; - if(ts->selectmode & SCE_SELECT_VERTEX) { + if(vc->scene->selectmode & SCE_SELECT_VERTEX) { if(bbsel) { EM_backbuf_checkAndSelectVerts(vc->em, selecting==LEFTMOUSE); } else { @@ -1677,7 +1674,7 @@ static void mesh_circle_select(ViewContext *vc, int selecting, short *mval, floa } } - if(ts->selectmode & SCE_SELECT_EDGE) { + if(vc->scene->selectmode & SCE_SELECT_EDGE) { if (bbsel) { EM_backbuf_checkAndSelectEdges(vc->em, selecting==LEFTMOUSE); } else { @@ -1685,7 +1682,7 @@ static void mesh_circle_select(ViewContext *vc, int selecting, short *mval, floa } } - if(ts->selectmode & SCE_SELECT_FACE) { + if(vc->scene->selectmode & SCE_SELECT_FACE) { if(bbsel) { EM_backbuf_checkAndSelectFaces(vc->em, selecting==LEFTMOUSE); } else { diff --git a/source/blender/editors/space_view3d/view3d_toolbar.c b/source/blender/editors/space_view3d/view3d_toolbar.c index ea365d59ac7..1e55f2e4a9a 100644 --- a/source/blender/editors/space_view3d/view3d_toolbar.c +++ b/source/blender/editors/space_view3d/view3d_toolbar.c @@ -120,6 +120,8 @@ static void redo_cb(bContext *C, void *arg_op, void *arg2) static void view3d_panel_operator_redo(const bContext *C, Panel *pa) { + /* XXX temp */ + extern void uiDefAutoButsRNA_single(const bContext *C, uiLayout *layout, PointerRNA *ptr); wmWindowManager *wm= CTX_wm_manager(C); wmOperator *op; PointerRNA ptr; @@ -134,7 +136,7 @@ static void view3d_panel_operator_redo(const bContext *C, Panel *pa) if(op==NULL) return; - if(op->type->poll && op->type->poll((bContext *)C)==0) + if(op->type->poll && op->type->poll(C)==0) return; uiBlockSetFunc(block, redo_cb, op, NULL); @@ -145,132 +147,13 @@ static void view3d_panel_operator_redo(const bContext *C, Panel *pa) } RNA_pointer_create(&wm->id, op->type->srna, op->properties, &ptr); - uiDefAutoButsRNA(C, pa->layout, &ptr, 1); + uiDefAutoButsRNA_single(C, pa->layout, &ptr); } -/* ******************* */ - -typedef struct CustomTool { - struct CustomTool *next, *prev; - char opname[OP_MAX_TYPENAME]; -} CustomTool; - -static void operator_call_cb(struct bContext *C, void *arg_listbase, void *arg2) -{ - wmOperatorType *ot= arg2; - - if(ot) { - CustomTool *ct= MEM_callocN(sizeof(CustomTool), "CustomTool"); - - BLI_addtail(arg_listbase, ct); - BLI_strncpy(ct->opname, ot->idname, OP_MAX_TYPENAME); - } - -} - -static void operator_search_cb(const struct bContext *C, void *arg, char *str, uiSearchItems *items) -{ - wmOperatorType *ot = WM_operatortype_first(); - - for(; ot; ot= ot->next) { - - if(BLI_strcasestr(ot->name, str)) { - if(ot->poll==NULL || ot->poll((bContext *)C)) { - - if(0==uiSearchItemAdd(items, ot->name, ot, 0)) - break; - } - } - } -} - - -/* ID Search browse menu, open */ -static uiBlock *tool_search_menu(bContext *C, ARegion *ar, void *arg_listbase) -{ - static char search[OP_MAX_TYPENAME]; - wmEvent event; - wmWindow *win= CTX_wm_window(C); - uiBlock *block; - uiBut *but; - - /* clear initial search string, then all items show */ - search[0]= 0; - - block= uiBeginBlock(C, ar, "_popup", UI_EMBOSS); - uiBlockSetFlag(block, UI_BLOCK_LOOP|UI_BLOCK_REDRAW|UI_BLOCK_RET_1); - - /* fake button, it holds space for search items */ - uiDefBut(block, LABEL, 0, "", 10, 15, 150, uiSearchBoxhHeight(), NULL, 0, 0, 0, 0, NULL); - - but= uiDefSearchBut(block, search, 0, ICON_VIEWZOOM, OP_MAX_TYPENAME, 10, 0, 150, 19, ""); - uiButSetSearchFunc(but, operator_search_cb, arg_listbase, operator_call_cb, NULL); - - uiBoundsBlock(block, 6); - uiBlockSetDirection(block, UI_DOWN); - uiEndBlock(C, block); - - event= *(win->eventstate); /* XXX huh huh? make api call */ - event.type= EVT_BUT_OPEN; - event.val= KM_PRESS; - event.customdata= but; - event.customdatafree= FALSE; - wm_event_add(win, &event); - - return block; -} - - -static void view3d_panel_tools(const bContext *C, Panel *pa) -{ - static ListBase tools= {NULL, NULL}; - Object *obedit= CTX_data_edit_object(C); -// Object *obact = CTX_data_active_object(C); - uiLayout *col; - - if(obedit) { - if(obedit->type==OB_MESH) { - - col= uiLayoutColumn(pa->layout, 1); - uiItemFullO(col, NULL, 0, "MESH_OT_spin", NULL, WM_OP_INVOKE_REGION_WIN); - uiItemFullO(col, NULL, 0, "MESH_OT_screw", NULL, WM_OP_INVOKE_REGION_WIN); - - if(tools.first) { - CustomTool *ct; - - for(ct= tools.first; ct; ct= ct->next) { - col= uiLayoutColumn(pa->layout, 1); - uiItemFullO(col, NULL, 0, ct->opname, NULL, WM_OP_INVOKE_REGION_WIN); - } - } - col= uiLayoutColumn(pa->layout, 1); - uiDefBlockBut(uiLayoutGetBlock(pa->layout), tool_search_menu, &tools, "Add Operator", 0, 0, UI_UNIT_X, UI_UNIT_Y, "Add tool"); - } - } - else { - - col= uiLayoutColumn(pa->layout, 1); - uiItemFullO(col, NULL, 0, "OBJECT_OT_delete", NULL, WM_OP_INVOKE_REGION_WIN); - uiItemFullO(col, NULL, 0, "OBJECT_OT_primitive_add", NULL, WM_OP_INVOKE_REGION_WIN); - - col= uiLayoutColumn(pa->layout, 1); - uiItemFullO(col, NULL, 0, "OBJECT_OT_parent_set", NULL, WM_OP_INVOKE_REGION_WIN); - uiItemFullO(col, NULL, 0, "OBJECT_OT_parent_clear", NULL, WM_OP_INVOKE_REGION_WIN); - - } -} - - void view3d_toolbar_register(ARegionType *art) { PanelType *pt; - pt= MEM_callocN(sizeof(PanelType), "spacetype view3d panel tools"); - strcpy(pt->idname, "VIEW3D_PT_tools"); - strcpy(pt->label, "Tools"); - pt->draw= view3d_panel_tools; - BLI_addtail(&art->paneltypes, pt); - pt= MEM_callocN(sizeof(PanelType), "spacetype view3d panel last operator"); strcpy(pt->idname, "VIEW3D_PT_last_operator"); strcpy(pt->label, "Last Operator"); diff --git a/source/blender/editors/space_view3d/view3d_view.c b/source/blender/editors/space_view3d/view3d_view.c index b57f4a91004..2db5f2c97fd 100644 --- a/source/blender/editors/space_view3d/view3d_view.c +++ b/source/blender/editors/space_view3d/view3d_view.c @@ -76,12 +76,11 @@ #include "UI_resources.h" #include "UI_view2d.h" -#include "GPU_draw.h" - #include "PIL_time.h" /* smoothview */ #include "view3d_intern.h" // own include + /* use this call when executing an operator, event system doesn't set for each event the opengl drawing context */ @@ -1431,9 +1430,6 @@ static int game_engine_exec(bContext *C, wmOperator *unused) Scene *startscene = CTX_data_scene(C); #if GAMEBLENDER == 1 - - view3d_operator_needs_opengl(C); - SaveState(C); StartKetsjiShell(C, 1); RestoreState(C); diff --git a/source/blender/editors/transform/Makefile b/source/blender/editors/transform/Makefile index 607038b413b..bc3e08a2ae8 100644 --- a/source/blender/editors/transform/Makefile +++ b/source/blender/editors/transform/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/transform/transform.c b/source/blender/editors/transform/transform.c index 3311fb7d0fe..674de81a9f5 100644 --- a/source/blender/editors/transform/transform.c +++ b/source/blender/editors/transform/transform.c @@ -1134,7 +1134,7 @@ void drawTransform(const struct bContext *C, struct ARegion *ar, void *arg) void saveTransform(bContext *C, TransInfo *t, wmOperator *op) { - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *sce = CTX_data_scene(C); int constraint_axis[3] = {0, 0, 0}; int proportional = 0; @@ -1195,8 +1195,8 @@ void saveTransform(bContext *C, TransInfo *t, wmOperator *op) // XXX If modal, save settings back in scene if (t->flag & T_MODAL) { - ts->prop_mode = t->prop_mode; - ts->proportional = proportional; + sce->prop_mode = t->prop_mode; + sce->proportional = proportional; if(t->spacetype == SPACE_VIEW3D) { @@ -2359,7 +2359,7 @@ static void ElementResize(TransInfo *t, TransData *td, float mat[3][3]) { } else if (t->flag & T_EDIT) { - if(t->around==V3D_LOCAL && (t->settings->selectmode & SCE_SELECT_FACE)) { + if(t->around==V3D_LOCAL && (t->scene->selectmode & SCE_SELECT_FACE)) { VECCOPY(center, td->center); } else { @@ -2660,7 +2660,7 @@ static void ElementRotation(TransInfo *t, TransData *td, float mat[3][3], short } else { /* !TODO! Make this if not rely on G */ - if(around==V3D_LOCAL && (t->settings->selectmode & SCE_SELECT_FACE)) { + if(around==V3D_LOCAL && (t->scene->selectmode & SCE_SELECT_FACE)) { center = td->center; } } @@ -3126,7 +3126,7 @@ static void headerTranslation(TransInfo *t, float vec[3], char *str) { sprintf(distvec, "%.4f", dist); if(t->flag & T_AUTOIK) { - short chainlen= t->settings->autoik_chainlen; + short chainlen= t->scene->toolsettings->autoik_chainlen; if(chainlen) sprintf(autoik, "AutoIK-Len: %d", chainlen); @@ -4251,7 +4251,7 @@ int Align(TransInfo *t, short mval[2]) VECCOPY(t->center, td->center); } else { - if(t->settings->selectmode & SCE_SELECT_FACE) { + if(t->scene->selectmode & SCE_SELECT_FACE) { VECCOPY(t->center, td->center); } } diff --git a/source/blender/editors/transform/transform.h b/source/blender/editors/transform/transform.h index 534f142734a..ee767fada58 100644 --- a/source/blender/editors/transform/transform.h +++ b/source/blender/editors/transform/transform.h @@ -257,7 +257,6 @@ typedef struct TransInfo { struct ScrArea *sa; struct ARegion *ar; struct Scene *scene; - struct ToolSettings *settings; struct wmTimer *animtimer; short mval[2]; /* current mouse position */ struct Object *obedit; diff --git a/source/blender/editors/transform/transform_conversions.c b/source/blender/editors/transform/transform_conversions.c index 490ce820b30..6c7aa1ee49d 100644 --- a/source/blender/editors/transform/transform_conversions.c +++ b/source/blender/editors/transform/transform_conversions.c @@ -777,7 +777,7 @@ static void pchan_autoik_adjust (bPoseChannel *pchan, short chainlen) /* change the chain-length of auto-ik */ void transform_autoik_update (TransInfo *t, short mode) { - short *chainlen= &t->settings->autoik_chainlen; + short *chainlen= &t->scene->toolsettings->autoik_chainlen; bPoseChannel *pchan; /* mode determines what change to apply to chainlen */ @@ -1631,7 +1631,7 @@ static void createTransParticleVerts(bContext *C, TransInfo *t) int count = 0, hasselected = 0; int propmode = t->flag & T_PROP_EDIT; - if(psys==NULL || t->settings->particle.selectmode==SCE_SELECT_PATH) return; + if(psys==NULL || t->scene->selectmode==SCE_SELECT_PATH) return; psmd = psys_get_modifier(ob,psys); @@ -2101,7 +2101,7 @@ void createTransBMeshVerts(TransInfo *t, BME_Mesh *bm, BME_TransData_Head *td) { static void createTransEditVerts(bContext *C, TransInfo *t) { - ToolSettings *ts = CTX_data_tool_settings(C); + Scene *scene = CTX_data_scene(C); TransData *tob = NULL; EditMesh *em = ((Mesh *)t->obedit->data)->edit_mesh; EditVert *eve; @@ -2119,7 +2119,7 @@ static void createTransEditVerts(bContext *C, TransInfo *t) } // transform now requires awareness for select mode, so we tag the f1 flags in verts - if(ts->selectmode & SCE_SELECT_VERTEX) { + if(scene->selectmode & SCE_SELECT_VERTEX) { for(eve= em->verts.first; eve; eve= eve->next) { if(eve->h==0 && (eve->f & SELECT)) eve->f1= SELECT; @@ -2127,7 +2127,7 @@ static void createTransEditVerts(bContext *C, TransInfo *t) eve->f1= 0; } } - else if(ts->selectmode & SCE_SELECT_EDGE) { + else if(scene->selectmode & SCE_SELECT_EDGE) { EditEdge *eed; for(eve= em->verts.first; eve; eve= eve->next) eve->f1= 0; for(eed= em->edges.first; eed; eed= eed->next) { @@ -4672,14 +4672,8 @@ void special_aftertrans_update(TransInfo *t) if (base->flag & SELECT && (t->mode != TFM_DUMMY)) { /* pointcache refresh */ - if (BKE_ptcache_object_reset(scene, ob, PTCACHE_RESET_DEPSGRAPH)) + if (BKE_ptcache_object_reset(ob, PTCACHE_RESET_DEPSGRAPH)) ob->recalc |= OB_RECALC_DATA; - - /* Needed for proper updating of "quick cached" dynamics. */ - /* Creates troubles for moving animated objects without */ - /* autokey though, probably needed is an anim sys override? */ - /* Please remove if some other solution is found. -jahka */ - DAG_object_flush_update(scene, ob, OB_RECALC_OB); /* Set autokey if necessary */ if (!cancelled) diff --git a/source/blender/editors/transform/transform_generics.c b/source/blender/editors/transform/transform_generics.c index e157d7f68f9..171665c9282 100644 --- a/source/blender/editors/transform/transform_generics.c +++ b/source/blender/editors/transform/transform_generics.c @@ -665,7 +665,6 @@ void resetTransRestrictions(TransInfo *t) int initTransInfo (bContext *C, TransInfo *t, wmOperator *op, wmEvent *event) { Scene *sce = CTX_data_scene(C); - ToolSettings *ts = CTX_data_tool_settings(C); ARegion *ar = CTX_wm_region(C); ScrArea *sa = CTX_wm_area(C); Object *obedit = CTX_data_edit_object(C); @@ -680,7 +679,6 @@ int initTransInfo (bContext *C, TransInfo *t, wmOperator *op, wmEvent *event) t->sa = sa; t->ar = ar; t->obedit = obedit; - t->settings = ts; t->data = NULL; t->ext = NULL; @@ -754,10 +752,9 @@ int initTransInfo (bContext *C, TransInfo *t, wmOperator *op, wmEvent *event) } else if(t->spacetype==SPACE_IMAGE || t->spacetype==SPACE_NODE) { - SpaceImage *sima = sa->spacedata.first; // XXX for now, get View2D from the active region t->view = &ar->v2d; - t->around = sima->around; + t->around = ar->v2d.around; } else { @@ -777,7 +774,7 @@ int initTransInfo (bContext *C, TransInfo *t, wmOperator *op, wmEvent *event) // Need stuff to take it from edit mesh or whatnot here else { - if (t->obedit && t->obedit->type == OB_MESH && ts->editbutflag & B_MESH_X_MIRROR) + if (t->obedit && t->obedit->type == OB_MESH && sce->toolsettings->editbutflag & B_MESH_X_MIRROR) { t->flag |= T_MIRROR; } @@ -797,10 +794,10 @@ int initTransInfo (bContext *C, TransInfo *t, wmOperator *op, wmEvent *event) } else { - if ((t->options & CTX_NO_PET) == 0 && (ts->proportional)) { + if ((t->options & CTX_NO_PET) == 0 && (sce->proportional)) { t->flag |= T_PROP_EDIT; - if(ts->proportional == 2) + if(sce->proportional == 2) t->flag |= T_PROP_CONNECTED; // yes i know, has to become define } } @@ -811,7 +808,7 @@ int initTransInfo (bContext *C, TransInfo *t, wmOperator *op, wmEvent *event) } else { - t->prop_size = ts->proportional_size; + t->prop_size = sce->toolsettings->proportional_size; } if (op && RNA_struct_find_property(op->ptr, "proportional_editing_falloff") && RNA_property_is_set(op->ptr, "proportional_editing_falloff")) @@ -820,7 +817,7 @@ int initTransInfo (bContext *C, TransInfo *t, wmOperator *op, wmEvent *event) } else { - t->prop_mode = ts->prop_mode; + t->prop_mode = sce->prop_mode; } /* TRANSFORM_FIX_ME rna restrictions */ diff --git a/source/blender/editors/transform/transform_input.c b/source/blender/editors/transform/transform_input.c index 631eb1eb134..4d721a83c78 100644 --- a/source/blender/editors/transform/transform_input.c +++ b/source/blender/editors/transform/transform_input.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: transform_input.c 18142 2008-12-29 07:19:16Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -26,7 +26,6 @@ #include <math.h> #include "DNA_screen_types.h" -#include "DNA_windowmanager_types.h" #include "BLI_arithb.h" diff --git a/source/blender/editors/transform/transform_ndofinput.c b/source/blender/editors/transform/transform_ndofinput.c index 9c2a1a7db6d..c52492ebd6b 100644 --- a/source/blender/editors/transform/transform_ndofinput.c +++ b/source/blender/editors/transform/transform_ndofinput.c @@ -31,7 +31,6 @@ #include "BKE_utildefines.h" /* ABS */ #include "DNA_view3d_types.h" /* for G.vd (view3d) */ -#include "DNA_windowmanager_types.h" /* for G.vd (view3d) */ #include "WM_types.h" diff --git a/source/blender/editors/transform/transform_numinput.c b/source/blender/editors/transform/transform_numinput.c index f5f1d5fac9e..34976105db3 100644 --- a/source/blender/editors/transform/transform_numinput.c +++ b/source/blender/editors/transform/transform_numinput.c @@ -34,7 +34,6 @@ #include "BKE_utildefines.h" /* ABS */ #include "WM_types.h" -#include "DNA_windowmanager_types.h" #include "transform.h" diff --git a/source/blender/editors/transform/transform_ops.c b/source/blender/editors/transform/transform_ops.c index 9e4115f38f0..e697b6dfa7d 100644 --- a/source/blender/editors/transform/transform_ops.c +++ b/source/blender/editors/transform/transform_ops.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: transform_ops.c 17542 2008-11-23 15:27:53Z theeth $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/editors/transform/transform_snap.c b/source/blender/editors/transform/transform_snap.c index 0b9a176dbdf..72901110388 100644 --- a/source/blender/editors/transform/transform_snap.c +++ b/source/blender/editors/transform/transform_snap.c @@ -210,7 +210,7 @@ int handleSnapping(TransInfo *t, wmEvent *event) if (BIF_snappingSupported(t->obedit) && event->type == TABKEY && event->shift) { /* toggle snap and reinit */ - t->settings->snap_flag ^= SCE_SNAP; + t->scene->snap_flag ^= SCE_SNAP; initSnapping(t, NULL); status = 1; } @@ -282,10 +282,10 @@ int validSnappingNormal(TransInfo *t) void initSnapping(TransInfo *t, wmOperator *op) { - ToolSettings *ts = t->settings; + Scene *scene = t->scene; Object *obedit = t->obedit; int snapping = 0; - short snap_mode = t->settings->snap_target; + short snap_mode = t->scene->snap_target; resetSnapping(t); @@ -310,8 +310,8 @@ void initSnapping(TransInfo *t, wmOperator *op) } else { - snapping = ((ts->snap_flag & SCE_SNAP) == SCE_SNAP); - t->tsnap.align = ((t->settings->snap_flag & SCE_SNAP_ROTATE) == SCE_SNAP_ROTATE); + snapping = ((scene->snap_flag & SCE_SNAP) == SCE_SNAP); + t->tsnap.align = ((t->scene->snap_flag & SCE_SNAP_ROTATE) == SCE_SNAP_ROTATE); } if ((t->spacetype == SPACE_VIEW3D || t->spacetype == SPACE_IMAGE) && // Only 3D view or UV @@ -542,7 +542,7 @@ void CalcSnapGeometry(TransInfo *t, float *vec) int dist = SNAP_MIN_DISTANCE; // Use a user defined value here SnapMode mode; - if (t->settings->snap_mode == SCE_SNAP_MODE_VOLUME) + if (t->scene->snap_mode == SCE_SNAP_MODE_VOLUME) { ListBase depth_peels; DepthPeel *p1, *p2; @@ -575,7 +575,7 @@ void CalcSnapGeometry(TransInfo *t, float *vec) p1->flag = 1; /* if peeling objects, take the first and last from each object */ - if (t->settings->snap_flag & SCE_SNAP_PEEL_OBJECT) + if (t->scene->snap_flag & SCE_SNAP_PEEL_OBJECT) { DepthPeel *peel; for (peel = p1->next; peel; peel = peel->next) @@ -1346,7 +1346,6 @@ int snapDerivedMesh(short snap_mode, ARegion *ar, Object *ob, DerivedMesh *dm, E int snapObject(Scene *scene, ARegion *ar, Object *ob, int editobject, float obmat[][4], float ray_start[3], float ray_normal[3], short mval[2], float *loc, float *no, int *dist, float *depth) { - ToolSettings *ts= scene->toolsettings; int retval = 0; if (ob->type == OB_MESH) { @@ -1364,13 +1363,13 @@ int snapObject(Scene *scene, ARegion *ar, Object *ob, int editobject, float obma dm = mesh_get_derived_final(scene, ob, CD_MASK_BAREMESH); } - retval = snapDerivedMesh(ts->snap_mode, ar, ob, dm, em, obmat, ray_start, ray_normal, mval, loc, no, dist, depth); + retval = snapDerivedMesh(scene->snap_mode, ar, ob, dm, em, obmat, ray_start, ray_normal, mval, loc, no, dist, depth); dm->release(dm); } else if (ob->type == OB_ARMATURE) { - retval = snapArmature(ts->snap_mode, ar, ob, ob->data, obmat, ray_start, ray_normal, mval, loc, no, dist, depth); + retval = snapArmature(scene->snap_mode, ar, ob, ob->data, obmat, ray_start, ray_normal, mval, loc, no, dist, depth); } return retval; diff --git a/source/blender/editors/util/Makefile b/source/blender/editors/util/Makefile index 303079daeee..da701dc5d86 100644 --- a/source/blender/editors/util/Makefile +++ b/source/blender/editors/util/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/util/undo.c b/source/blender/editors/util/undo.c index 1d79c542fa9..62ce76a7614 100644 --- a/source/blender/editors/util/undo.c +++ b/source/blender/editors/util/undo.c @@ -183,8 +183,6 @@ void ED_undo_redo(bContext *C) static int ed_undo_exec(bContext *C, wmOperator *op) { - /* "last operator" should disappear, later we can tie ths with undo stack nicer */ - WM_operator_stack_clear(C); return ed_undo_step(C, 1); } static int ed_redo_exec(bContext *C, wmOperator *op) diff --git a/source/blender/editors/uvedit/Makefile b/source/blender/editors/uvedit/Makefile index d589bbec3bc..b8a8f0bc8af 100644 --- a/source/blender/editors/uvedit/Makefile +++ b/source/blender/editors/uvedit/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14 2002-10-13 15:57:19Z hans $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/editors/uvedit/uvedit_draw.c b/source/blender/editors/uvedit/uvedit_draw.c index b811906f5e5..aded5a4cff9 100644 --- a/source/blender/editors/uvedit/uvedit_draw.c +++ b/source/blender/editors/uvedit/uvedit_draw.c @@ -102,19 +102,17 @@ static void drawcursor_sima(SpaceImage *sima, ARegion *ar) static int draw_uvs_face_check(Scene *scene) { - ToolSettings *ts= scene->toolsettings; - /* checks if we are selecting only faces */ - if(ts->uv_flag & UV_SYNC_SELECTION) { - if(ts->selectmode == SCE_SELECT_FACE) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { + if(scene->selectmode == SCE_SELECT_FACE) return 2; - else if(ts->selectmode & SCE_SELECT_FACE) + else if(scene->selectmode & SCE_SELECT_FACE) return 1; else return 0; } else - return (ts->uv_selectmode == UV_SELECT_FACE); + return (scene->toolsettings->uv_selectmode == UV_SELECT_FACE); } static void draw_uvs_shadow(SpaceImage *sima, Object *obedit) @@ -420,7 +418,7 @@ static void draw_uvs_other(SpaceImage *sima, Scene *scene, Object *obedit, MTFac /* draws uv's in the image space */ static void draw_uvs(SpaceImage *sima, Scene *scene, Object *obedit) { - ToolSettings *ts; + ToolSettings *settings; Mesh *me= obedit->data; EditMesh *em; EditFace *efa, *efa_act; @@ -434,13 +432,13 @@ static void draw_uvs(SpaceImage *sima, Scene *scene, Object *obedit) em= BKE_mesh_get_editmesh(me); activetf= EM_get_active_mtface(em, &efa_act, NULL, 0); /* will be set to NULL if hidden */ - ts= scene->toolsettings; + settings= scene->toolsettings; drawfaces= draw_uvs_face_check(scene); - if(ts->uv_flag & UV_SYNC_SELECTION) - interpedges= (ts->selectmode & SCE_SELECT_VERTEX); + if(settings->uv_flag & UV_SYNC_SELECTION) + interpedges= (scene->selectmode & SCE_SELECT_VERTEX); else - interpedges= (ts->uv_selectmode == UV_SELECT_VERTEX); + interpedges= (settings->uv_selectmode == UV_SELECT_VERTEX); /* draw other uvs */ if(sima->flag & SI_DRAW_OTHER) @@ -456,7 +454,7 @@ static void draw_uvs(SpaceImage *sima, Scene *scene, Object *obedit) /* when sync selection is enabled, all faces are drawn (except for hidden) * so if cage is the same as the final, theres no point in drawing this */ - if(!((ts->uv_flag & UV_SYNC_SELECTION) && (cagedm == finaldm))) + if(!((settings->uv_flag & UV_SYNC_SELECTION) && (cagedm == finaldm))) draw_uvs_dm_shadow(finaldm); /* release derivedmesh again */ diff --git a/source/blender/editors/uvedit/uvedit_ops.c b/source/blender/editors/uvedit/uvedit_ops.c index 7582145c63b..7dca4d34c48 100644 --- a/source/blender/editors/uvedit/uvedit_ops.c +++ b/source/blender/editors/uvedit/uvedit_ops.c @@ -191,9 +191,7 @@ static void uvedit_pixel_to_float(SpaceImage *sima, float *dist, float pixeldist int uvedit_face_visible_nolocal(Scene *scene, EditFace *efa) { - ToolSettings *ts= scene->toolsettings; - - if(ts->uv_flag & UV_SYNC_SELECTION) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) return (efa->h==0); else return (efa->h==0 && (efa->f & SELECT)); @@ -201,9 +199,7 @@ int uvedit_face_visible_nolocal(Scene *scene, EditFace *efa) int uvedit_face_visible(Scene *scene, Image *ima, EditFace *efa, MTFace *tf) { - ToolSettings *ts= scene->toolsettings; - - if(ts->uv_flag & UV_SHOW_SAME_IMAGE) + if(scene->toolsettings->uv_flag & UV_SHOW_SAME_IMAGE) return (tf->tpage==ima)? uvedit_face_visible_nolocal(scene, efa): 0; else return uvedit_face_visible_nolocal(scene, efa); @@ -211,9 +207,7 @@ int uvedit_face_visible(Scene *scene, Image *ima, EditFace *efa, MTFace *tf) int uvedit_face_selected(Scene *scene, EditFace *efa, MTFace *tf) { - ToolSettings *ts= scene->toolsettings; - - if(ts->uv_flag & UV_SYNC_SELECTION) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) return (efa->f & SELECT); else return (!(~tf->flag & (TF_SEL1|TF_SEL2|TF_SEL3)) &&(!efa->v4 || tf->flag & TF_SEL4)); @@ -221,9 +215,7 @@ int uvedit_face_selected(Scene *scene, EditFace *efa, MTFace *tf) void uvedit_face_select(Scene *scene, EditFace *efa, MTFace *tf) { - ToolSettings *ts= scene->toolsettings; - - if(ts->uv_flag & UV_SYNC_SELECTION) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) EM_select_face(efa, 1); else tf->flag |= (TF_SEL1|TF_SEL2|TF_SEL3|TF_SEL4); @@ -231,9 +223,7 @@ void uvedit_face_select(Scene *scene, EditFace *efa, MTFace *tf) void uvedit_face_deselect(Scene *scene, EditFace *efa, MTFace *tf) { - ToolSettings *ts= scene->toolsettings; - - if(ts->uv_flag & UV_SYNC_SELECTION) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) EM_select_face(efa, 0); else tf->flag &= ~(TF_SEL1|TF_SEL2|TF_SEL3|TF_SEL4); @@ -241,13 +231,12 @@ void uvedit_face_deselect(Scene *scene, EditFace *efa, MTFace *tf) int uvedit_edge_selected(Scene *scene, EditFace *efa, MTFace *tf, int i) { - ToolSettings *ts= scene->toolsettings; int nvert= (efa->v4)? 4: 3; - if(ts->uv_flag & UV_SYNC_SELECTION) { - if(ts->selectmode == SCE_SELECT_FACE) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { + if(scene->selectmode == SCE_SELECT_FACE) return (efa->f & SELECT); - else if(ts->selectmode == SCE_SELECT_EDGE) + else if(scene->selectmode == SCE_SELECT_EDGE) return (*(&efa->e1 + i))->f & SELECT; else return (((efa->v1 + i)->f & SELECT) && ((efa->v1 + (i+1)%nvert)->f & SELECT)); @@ -258,13 +247,12 @@ int uvedit_edge_selected(Scene *scene, EditFace *efa, MTFace *tf, int i) void uvedit_edge_select(Scene *scene, EditFace *efa, MTFace *tf, int i) { - ToolSettings *ts= scene->toolsettings; int nvert= (efa->v4)? 4: 3; - if(ts->uv_flag & UV_SYNC_SELECTION) { - if(ts->selectmode == SCE_SELECT_FACE) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { + if(scene->selectmode == SCE_SELECT_FACE) EM_select_face(efa, 1); - else if(ts->selectmode == SCE_SELECT_EDGE) + else if(scene->selectmode == SCE_SELECT_EDGE) EM_select_edge((*(&efa->e1 + i)), 1); else { (efa->v1 + i)->f |= SELECT; @@ -277,13 +265,12 @@ void uvedit_edge_select(Scene *scene, EditFace *efa, MTFace *tf, int i) void uvedit_edge_deselect(Scene *scene, EditFace *efa, MTFace *tf, int i) { - ToolSettings *ts= scene->toolsettings; int nvert= (efa->v4)? 4: 3; - if(ts->uv_flag & UV_SYNC_SELECTION) { - if(ts->selectmode == SCE_SELECT_FACE) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { + if(scene->selectmode == SCE_SELECT_FACE) EM_select_face(efa, 0); - else if(ts->selectmode == SCE_SELECT_EDGE) + else if(scene->selectmode == SCE_SELECT_EDGE) EM_select_edge((*(&efa->e1 + i)), 0); else { (efa->v1 + i)->f &= ~SELECT; @@ -296,10 +283,8 @@ void uvedit_edge_deselect(Scene *scene, EditFace *efa, MTFace *tf, int i) int uvedit_uv_selected(Scene *scene, EditFace *efa, MTFace *tf, int i) { - ToolSettings *ts= scene->toolsettings; - - if(ts->uv_flag & UV_SYNC_SELECTION) { - if(ts->selectmode == SCE_SELECT_FACE) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { + if(scene->selectmode == SCE_SELECT_FACE) return (efa->f & SELECT); else return (*(&efa->v1 + i))->f & SELECT; @@ -310,10 +295,8 @@ int uvedit_uv_selected(Scene *scene, EditFace *efa, MTFace *tf, int i) void uvedit_uv_select(Scene *scene, EditFace *efa, MTFace *tf, int i) { - ToolSettings *ts= scene->toolsettings; - - if(ts->uv_flag & UV_SYNC_SELECTION) { - if(ts->selectmode == SCE_SELECT_FACE) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { + if(scene->selectmode == SCE_SELECT_FACE) EM_select_face(efa, 1); else (*(&efa->v1 + i))->f |= SELECT; @@ -324,10 +307,8 @@ void uvedit_uv_select(Scene *scene, EditFace *efa, MTFace *tf, int i) void uvedit_uv_deselect(Scene *scene, EditFace *efa, MTFace *tf, int i) { - ToolSettings *ts= scene->toolsettings; - - if(ts->uv_flag & UV_SYNC_SELECTION) { - if(ts->selectmode == SCE_SELECT_FACE) + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { + if(scene->selectmode == SCE_SELECT_FACE) EM_select_face(efa, 0); else (*(&efa->v1 + i))->f &= ~SELECT; @@ -1308,7 +1289,6 @@ void UV_OT_stitch(wmOperatorType *ot) static int select_inverse_exec(bContext *C, wmOperator *op) { Scene *scene; - ToolSettings *ts; Object *obedit; EditMesh *em; EditFace *efa; @@ -1316,12 +1296,11 @@ static int select_inverse_exec(bContext *C, wmOperator *op) MTFace *tf; scene= CTX_data_scene(C); - ts= CTX_data_tool_settings(C); obedit= CTX_data_edit_object(C); em= BKE_mesh_get_editmesh((Mesh*)obedit->data); ima= CTX_data_edit_image(C); - if(ts->uv_flag & UV_SYNC_SELECTION) { + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { EM_select_swap(em); } else { @@ -1360,7 +1339,6 @@ void UV_OT_select_invert(wmOperatorType *ot) static int de_select_all_exec(bContext *C, wmOperator *op) { Scene *scene; - ToolSettings *ts; Object *obedit; EditMesh *em; EditFace *efa; @@ -1369,12 +1347,11 @@ static int de_select_all_exec(bContext *C, wmOperator *op) int sel; scene= CTX_data_scene(C); - ts= CTX_data_tool_settings(C); obedit= CTX_data_edit_object(C); em= BKE_mesh_get_editmesh((Mesh*)obedit->data); ima= CTX_data_edit_image(C); - if(ts->uv_flag & UV_SYNC_SELECTION) { + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { EM_toggle_select_all(em); } else { @@ -1454,7 +1431,6 @@ static int mouse_select(bContext *C, float co[2], int extend, int loop) { SpaceImage *sima= (SpaceImage*)CTX_wm_space_data(C); Scene *scene= CTX_data_scene(C); - ToolSettings *ts= CTX_data_tool_settings(C); Object *obedit= CTX_data_edit_object(C); Image *ima= CTX_data_edit_image(C); EditMesh *em= BKE_mesh_get_editmesh((Mesh*)obedit->data); @@ -1469,12 +1445,12 @@ static int mouse_select(bContext *C, float co[2], int extend, int loop) uvedit_pixel_to_float(sima, penalty, 5.0f); /* retrieve operation mode */ - if(ts->uv_flag & UV_SYNC_SELECTION) { + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { sync= 1; - if(ts->selectmode & SCE_SELECT_FACE) + if(scene->selectmode & SCE_SELECT_FACE) selectmode= UV_SELECT_FACE; - else if(ts->selectmode & SCE_SELECT_EDGE) + else if(scene->selectmode & SCE_SELECT_EDGE) selectmode= UV_SELECT_EDGE; else selectmode= UV_SELECT_VERTEX; @@ -1483,7 +1459,7 @@ static int mouse_select(bContext *C, float co[2], int extend, int loop) } else { sync= 0; - selectmode= ts->uv_selectmode; + selectmode= scene->toolsettings->uv_selectmode; sticky= sima->sticky; } @@ -1705,7 +1681,7 @@ static int mouse_select(bContext *C, float co[2], int extend, int loop) if(sync) { /* flush for mesh selection */ - if(ts->selectmode != SCE_SELECT_FACE) { + if(scene->selectmode != SCE_SELECT_FACE) { if(flush==1) EM_select_flush(em); else if(flush==-1) EM_deselect_flush(em); } @@ -1818,14 +1794,13 @@ static int select_linked_exec(bContext *C, wmOperator *op) { SpaceImage *sima= (SpaceImage*)CTX_wm_space_data(C); Scene *scene= CTX_data_scene(C); - ToolSettings *ts= CTX_data_tool_settings(C); Object *obedit= CTX_data_edit_object(C); Image *ima= CTX_data_edit_image(C); EditMesh *em= BKE_mesh_get_editmesh((Mesh*)obedit->data); float limit[2]; int extend; - if(ts->uv_flag & UV_SYNC_SELECTION) { + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { BKE_report(op->reports, RPT_ERROR, "Can't select linked when sync selection is enabled."); BKE_mesh_end_editmesh(obedit->data, em); return OPERATOR_CANCELLED; @@ -1863,14 +1838,13 @@ void UV_OT_select_linked(wmOperatorType *ot) static int unlink_selection_exec(bContext *C, wmOperator *op) { Scene *scene= CTX_data_scene(C); - ToolSettings *ts= CTX_data_tool_settings(C); Object *obedit= CTX_data_edit_object(C); Image *ima= CTX_data_edit_image(C); EditMesh *em= BKE_mesh_get_editmesh((Mesh*)obedit->data); EditFace *efa; MTFace *tf; - if(ts->uv_flag & UV_SYNC_SELECTION) { + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { BKE_report(op->reports, RPT_ERROR, "Can't unlink selection when sync selection is enabled."); BKE_mesh_end_editmesh(obedit->data, em); return OPERATOR_CANCELLED; @@ -1927,13 +1901,12 @@ static void uv_faces_do_sticky(bContext *C, SpaceImage *sima, Scene *scene, Obje * This only needs to be done when the Mesh is not used for * selection (so for sticky modes, vertex or location based). */ - ToolSettings *ts= CTX_data_tool_settings(C); EditMesh *em= BKE_mesh_get_editmesh((Mesh*)obedit->data); EditFace *efa; MTFace *tf; int nverts, i; - if((ts->uv_flag & UV_SYNC_SELECTION)==0 && sima->sticky == SI_STICKY_VERTEX) { + if((scene->toolsettings->uv_flag & UV_SYNC_SELECTION)==0 && sima->sticky == SI_STICKY_VERTEX) { /* Tag all verts as untouched, then touch the ones that have a face center * in the loop and select all MTFace UV's that use a touched vert. */ EditVert *eve; @@ -1964,7 +1937,7 @@ static void uv_faces_do_sticky(bContext *C, SpaceImage *sima, Scene *scene, Obje } } } - else if((ts->uv_flag & UV_SYNC_SELECTION)==0 && sima->sticky == SI_STICKY_LOC) { + else if((scene->toolsettings->uv_flag & UV_SYNC_SELECTION)==0 && sima->sticky == SI_STICKY_LOC) { EditFace *efa_vlist; MTFace *tf_vlist; UvMapVert *start_vlist=NULL, *vlist_iter; @@ -2035,7 +2008,7 @@ static void uv_faces_do_sticky(bContext *C, SpaceImage *sima, Scene *scene, Obje EM_free_uv_vert_map(vmap); } - else { /* SI_STICKY_DISABLE or ts->uv_flag & UV_SYNC_SELECTION */ + else { /* SI_STICKY_DISABLE or scene->toolsettings->uv_flag & UV_SYNC_SELECTION */ for(efa= em->faces.first; efa; efa= efa->next) { if(efa->tmp.l) { tf = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE); @@ -2053,7 +2026,6 @@ static int border_select_exec(bContext *C, wmOperator *op) { SpaceImage *sima= (SpaceImage*)CTX_wm_space_data(C); Scene *scene= CTX_data_scene(C); - ToolSettings *ts= CTX_data_tool_settings(C); Object *obedit= CTX_data_edit_object(C); Image *ima= CTX_data_edit_image(C); ARegion *ar= CTX_wm_region(C); @@ -2077,10 +2049,10 @@ static int border_select_exec(bContext *C, wmOperator *op) select= (RNA_int_get(op->ptr, "event_type") == LEFTMOUSE); // XXX hardcoded pinned= RNA_boolean_get(op->ptr, "pinned"); - if(ts->uv_flag & UV_SYNC_SELECTION) - faces= (ts->selectmode == SCE_SELECT_FACE); + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) + faces= (scene->selectmode == SCE_SELECT_FACE); else - faces= (ts->uv_selectmode == UV_SELECT_FACE); + faces= (scene->toolsettings->uv_selectmode == UV_SELECT_FACE); /* do actual selection */ if(faces && !pinned) { @@ -2112,7 +2084,7 @@ static int border_select_exec(bContext *C, wmOperator *op) for(efa= em->faces.first; efa; efa= efa->next) { tface= CustomData_em_get(&em->fdata, efa->data, CD_MTFACE); if(uvedit_face_visible(scene, ima, efa, tface)) { - if(!pinned || (ts->uv_flag & UV_SYNC_SELECTION) ) { + if(!pinned || (scene->toolsettings->uv_flag & UV_SYNC_SELECTION) ) { /* UV_SYNC_SELECTION - can't do pinned selection */ if(BLI_in_rctf(&rectf, tface->uv[0][0], tface->uv[0][1])) { if(select) uvedit_uv_select(scene, efa, tface, 0); @@ -2161,8 +2133,8 @@ static int border_select_exec(bContext *C, wmOperator *op) if(change) { /* make sure newly selected vert selection is updated*/ - if(ts->uv_flag & UV_SYNC_SELECTION) { - if(ts->selectmode != SCE_SELECT_FACE) { + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { + if(scene->selectmode != SCE_SELECT_FACE) { if(select) EM_select_flush(em); else EM_deselect_flush(em); } @@ -2696,14 +2668,14 @@ void UV_OT_select_pinned(wmOperatorType *ot) static int hide_exec(bContext *C, wmOperator *op) { SpaceImage *sima= (SpaceImage*)CTX_wm_space_data(C); - ToolSettings *ts= CTX_data_tool_settings(C); + Scene *scene= CTX_data_scene(C); Object *obedit= CTX_data_edit_object(C); EditMesh *em= BKE_mesh_get_editmesh((Mesh*)obedit->data); EditFace *efa; MTFace *tf; int swap= RNA_boolean_get(op->ptr, "unselected"); - if(ts->uv_flag & UV_SYNC_SELECTION) { + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { EM_hide_mesh(em, swap); WM_event_add_notifier(C, NC_OBJECT|ND_GEOM_SELECT, obedit); @@ -2839,14 +2811,14 @@ void UV_OT_hide(wmOperatorType *ot) static int reveal_exec(bContext *C, wmOperator *op) { SpaceImage *sima= (SpaceImage*)CTX_wm_space_data(C); - ToolSettings *ts= CTX_data_tool_settings(C); + Scene *scene= CTX_data_scene(C); Object *obedit= CTX_data_edit_object(C); EditMesh *em= BKE_mesh_get_editmesh((Mesh*)obedit->data); EditFace *efa; MTFace *tf; /* call the mesh function if we are in mesh sync sel */ - if(ts->uv_flag & UV_SYNC_SELECTION) { + if(scene->toolsettings->uv_flag & UV_SYNC_SELECTION) { EM_reveal_mesh(em); WM_event_add_notifier(C, NC_OBJECT|ND_GEOM_SELECT, obedit); diff --git a/source/blender/gpu/intern/Makefile b/source/blender/gpu/intern/Makefile index 3a3ac20ff6c..733ee3f764c 100644 --- a/source/blender/gpu/intern/Makefile +++ b/source/blender/gpu/intern/Makefile @@ -35,7 +35,7 @@ DIR = $(OCGDIR)/blender/$(LIBNAME) include nan_compile.mk -ifeq ($(OS),$(findstring $(OS), "darwin freebsd linux openbsd solaris windows")) +ifeq ($(OS),$(findstring $(OS), "beos darwin freebsd linux openbsd solaris windows")) CFLAGS += -funsigned-char endif diff --git a/source/blender/imbuf/intern/imbuf.h b/source/blender/imbuf/intern/imbuf.h index 7b5d668ce2b..bd2a0d3082f 100644 --- a/source/blender/imbuf/intern/imbuf.h +++ b/source/blender/imbuf/intern/imbuf.h @@ -51,7 +51,7 @@ #include <sys/mman.h> #endif -#if !defined(WIN32) +#if !defined(WIN32) && !defined(__BeOS) #define O_BINARY 0 #endif diff --git a/source/blender/imbuf/intern/readimage.c b/source/blender/imbuf/intern/readimage.c index 1a6ab104bcf..6df92f69fff 100644 --- a/source/blender/imbuf/intern/readimage.c +++ b/source/blender/imbuf/intern/readimage.c @@ -244,6 +244,26 @@ struct ImBuf *IMB_loadifffile(int file, int flags) { size = BLI_filesize(file); +#if defined(AMIGA) || defined(__BeOS) + mem= (int *)malloc(size); + if (mem==0) { + printf("Out of mem\n"); + return (0); + } + + if (read(file, mem, size)!=size){ + printf("Read Error\n"); + free(mem); + return (0); + } + + ibuf = IMB_ibImageFromMemory(mem, size, flags); + free(mem); + + /* for jpeg read */ + lseek(file, 0L, SEEK_SET); + +#else mem= (int *)mmap(0,size,PROT_READ,MAP_SHARED,file,0); if (mem==(int *)-1){ printf("Couldn't get mapping\n"); @@ -255,6 +275,7 @@ struct ImBuf *IMB_loadifffile(int file, int flags) { if (munmap( (void *) mem, size)){ printf("Couldn't unmap file.\n"); } +#endif return(ibuf); } diff --git a/source/blender/makesdna/DNA_object_force.h b/source/blender/makesdna/DNA_object_force.h index 88d9894cf7a..718d1a17834 100644 --- a/source/blender/makesdna/DNA_object_force.h +++ b/source/blender/makesdna/DNA_object_force.h @@ -33,8 +33,6 @@ #ifdef __cplusplus extern "C" { #endif - -#include "DNA_listBase.h" typedef struct PartDeflect { short deflect; /* Deflection flag - does mesh deflect particles*/ @@ -74,26 +72,12 @@ typedef struct PartDeflect { int seed; /* wind noise random seed */ } PartDeflect; -typedef struct PTCacheMem { - struct PTCacheMem *next, *prev; - int frame, totpoint; - float *data; /* data points */ - void *xdata; /* extra data */ -} PTCacheMem; - typedef struct PointCache { int flag; /* generic flag */ - int step; /* frames between cached frames */ int simframe; /* current frame of simulation (only if SIMULATION_VALID) */ int startframe; /* simulation start frame */ int endframe; /* simulation end frame */ int editframe; /* frame being edited (runtime only) */ - int last_exact; /* last exact frame that's cached */ - int xdata_type; /* type of extra data */ - char name[64]; - char prev_name[64]; - char info[64]; - struct ListBase mem_cache; } PointCache; typedef struct SBVertex { @@ -263,12 +247,6 @@ typedef struct SoftBody { #define PTCACHE_BAKING 8 #define PTCACHE_BAKE_EDIT 16 #define PTCACHE_BAKE_EDIT_ACTIVE 32 -#define PTCACHE_DISK_CACHE 64 -#define PTCACHE_QUICK_CACHE 128 -#define PTCACHE_FRAMES_SKIPPED 256 - -/* PTCACHE_OUTDATED + PTCACHE_FRAMES_SKIPPED */ -#define PTCACHE_REDO_NEEDED 258 /* ob->softflag */ #define OB_SB_ENABLE 1 diff --git a/source/blender/makesdna/DNA_particle_types.h b/source/blender/makesdna/DNA_particle_types.h index 05f1cc1f351..6805082d094 100644 --- a/source/blender/makesdna/DNA_particle_types.h +++ b/source/blender/makesdna/DNA_particle_types.h @@ -34,8 +34,6 @@ #include "DNA_ID.h" -struct AnimData; - typedef struct HairKey { float co[3]; /* location of hair vertex */ float time; /* time along hair, default 0-100 */ @@ -102,7 +100,6 @@ typedef struct ParticleData { typedef struct ParticleSettings { ID id; - struct AnimData *adt; int flag; short type, from, distr; @@ -170,7 +167,7 @@ typedef struct ParticleSettings { struct Group *eff_group; struct Object *dup_ob; struct Object *bb_ob; - struct Ipo *ipo; // xxx depreceated... old animation system + struct Ipo *ipo; struct PartDeflect *pd; struct PartDeflect *pd2; } ParticleSettings; @@ -195,7 +192,6 @@ typedef struct ParticleSystem{ /* note, make sure all (runtime) are NULL's in struct Object *target_ob; struct Object *keyed_ob; struct Object *lattice; - struct Object *parent; /* particles from global space -> parent space */ struct ListBase effectors, reactevents; /* runtime */ diff --git a/source/blender/makesdna/DNA_radio_types.h b/source/blender/makesdna/DNA_radio_types.h new file mode 100644 index 00000000000..4219bf59b93 --- /dev/null +++ b/source/blender/makesdna/DNA_radio_types.h @@ -0,0 +1,62 @@ +/** + * radio_types.h dec 2000 Nzc + * + * All type defs for the Blender core. + * + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + * + */ + +#ifndef DNA_RADIO_TYPES_H +#define DNA_RADIO_TYPES_H + +typedef struct Radio { + short hemires, maxiter; + short drawtype, flag; /* bit 0 and 1: show limits */ + short subshootp, subshoote, nodelim, maxsublamp; + short pama, pami, elma, elmi; /* patch and elem limits */ + int maxnode; + float convergence; + float radfac, gamma; /* for display */ + +} Radio; + + +/* **************** RADIOSITY ********************* */ + +/* draw type */ +#define RAD_WIREFRAME 0 +#define RAD_SOLID 1 +#define RAD_GOURAUD 2 + +/* flag */ +#define RAD_SHOWLIMITS 1 +#define RAD_SHOWZ 2 + +#endif + diff --git a/source/blender/makesdna/DNA_scene_types.h b/source/blender/makesdna/DNA_scene_types.h index 9a3ef758bd3..e8279604100 100644 --- a/source/blender/makesdna/DNA_scene_types.h +++ b/source/blender/makesdna/DNA_scene_types.h @@ -39,6 +39,7 @@ extern "C" { #include "DNA_scriptlink_types.h" #include "DNA_ID.h" +struct Radio; struct Object; struct World; struct Scene; @@ -47,7 +48,6 @@ struct Group; struct Text; struct bNodeTree; struct AnimData; -struct Editing; typedef struct Base { struct Base *next, *prev; @@ -158,7 +158,7 @@ typedef struct SceneRenderLayer { #define SCE_PASS_REFRACT 1024 #define SCE_PASS_INDEXOB 2048 #define SCE_PASS_UV 4096 -#define SCE_PASS_RADIO 8192 /* Radio removed, can use for new GI? */ +#define SCE_PASS_RADIO 8192 #define SCE_PASS_MIST 16384 /* note, srl->passflag is treestore element 'nr' in outliner, short still... */ @@ -385,8 +385,6 @@ typedef struct ParticleEditSettings { float emitterdist; int draw_timed; - - int selectmode, pad; } ParticleEditSettings; typedef struct TransformOrientation { @@ -446,19 +444,14 @@ typedef struct ToolSettings { short editbutflag; /*Triangle to Quad conversion threshold*/ float jointrilimit; - /* Editmode Tools */ + /* Extrude Tools */ float degr; short step; short turn; - float extr_offs; /* extrude offset */ - float doublimit; /* remove doubles limit */ - float normalsize; /* size of normals */ - short automerge; - - /* Selection Mode for Mesh */ - short selectmode; - + float extr_offs; + float doublimit; + /* Primitive Settings */ /* UV Sphere */ short segments; @@ -494,11 +487,8 @@ typedef struct ToolSettings { /* Select Group Threshold */ float select_thresh; - /* Graph Editor */ + /* IPO-Editor */ float clean_thresh; - - /* Auto-Keying Mode */ - short autokey_mode, pad2; /* defines in DNA_userdef_types.h */ /* Retopo */ char retopo_mode; @@ -525,6 +515,7 @@ typedef struct ToolSettings { char skgen_postpro_passes; char skgen_subdivisions[3]; char skgen_multi_level; + int skgen_pad; /* Skeleton Sketching */ struct Object *skgen_template; @@ -538,10 +529,7 @@ typedef struct ToolSettings { /* Alt+RMB option */ char edge_mode; - - /* transform */ - short snap_mode, snap_flag, snap_target; - short proportional, prop_mode; + char pad3[2]; } ToolSettings; typedef struct bStats { @@ -562,22 +550,29 @@ typedef struct Scene { struct Image *ima; ListBase base; - struct Base *basact; /* active base */ + struct Base *basact; struct Object *obedit; /* name replaces old G.obedit */ - float cursor[3]; /* 3d cursor location */ + float cursor[3]; float twcent[3]; /* center for transform widget */ float twmin[3], twmax[3]; /* boundbox of selection for transform widget */ unsigned int lay; + /* editmode stuff */ + float editbutsize; /* size of normals */ + short selectmode; /* for mesh only! */ + short proportional, prop_mode; + short automerge, pad5; short flag; /* various settings */ + short autokey_mode; /* mode for autokeying (defines in DNA_userdef_types.h) */ short use_nodes; struct bNodeTree *nodetree; - struct Editing *ed; /* sequence editor data is allocated here */ + void *ed; /* sequence editor data is allocated here */ + struct Radio *radio; struct GameFraming framing; @@ -587,20 +582,20 @@ typedef struct Scene { /* migrate or replace? depends on some internal things... */ /* no, is on the right place (ton) */ struct RenderData r; - struct AudioData audio; /* DEPRECATED 2.5 */ + struct AudioData audio; /* DEPRICATED 2.5 */ ScriptLink scriptlink; ListBase markers; ListBase transform_spaces; + short jumpframe; + short snap_mode, snap_flag, snap_target; /* none of the dependancy graph vars is mean to be saved */ struct DagForest *theDag; short dagisvalid, dagflags; - short recalc; /* recalc = counterpart of ob->recalc */ - - short jumpframe; + short pad4, recalc; /* recalc = counterpart of ob->recalc */ /* frame step. */ int frame_step; @@ -806,27 +801,27 @@ typedef struct Scene { /* base->flag is in DNA_object_types.h */ -/* toolsettings->snap_flag */ +/* scene->snap_flag */ #define SCE_SNAP 1 #define SCE_SNAP_ROTATE 2 #define SCE_SNAP_PEEL_OBJECT 4 -/* toolsettings->snap_target */ +/* scene->snap_target */ #define SCE_SNAP_TARGET_CLOSEST 0 #define SCE_SNAP_TARGET_CENTER 1 #define SCE_SNAP_TARGET_MEDIAN 2 #define SCE_SNAP_TARGET_ACTIVE 3 -/* toolsettings->snap_mode */ +/* scene->snap_mode */ #define SCE_SNAP_MODE_VERTEX 0 #define SCE_SNAP_MODE_EDGE 1 #define SCE_SNAP_MODE_FACE 2 #define SCE_SNAP_MODE_VOLUME 3 -/* toolsettings->selectmode */ +/* sce->selectmode */ #define SCE_SELECT_VERTEX 1 /* for mesh */ #define SCE_SELECT_EDGE 2 #define SCE_SELECT_FACE 4 -/* toolsettings->particle.selectmode for particles */ +/* sce->selectmode for particles */ #define SCE_SELECT_PATH 1 #define SCE_SELECT_POINT 2 #define SCE_SELECT_END 4 @@ -834,7 +829,7 @@ typedef struct Scene { /* sce->recalc (now in use by previewrender) */ #define SCE_PRV_CHANGED 1 -/* toolsettings->prop_mode (proportional falloff) */ +/* sce->prop_mode (proportional falloff) */ #define PROP_SMOOTH 0 #define PROP_SPHERE 1 #define PROP_ROOT 2 @@ -901,7 +896,7 @@ typedef enum SculptFlags { /* toolsettings->uv_selectmode */ #define UV_SELECT_VERTEX 1 -#define UV_SELECT_EDGE 2 +#define UV_SELECT_EDGE 2 /* not implemented */ #define UV_SELECT_FACE 4 #define UV_SELECT_ISLAND 8 diff --git a/source/blender/makesdna/DNA_space_types.h b/source/blender/makesdna/DNA_space_types.h index 9dc7e07a95c..416acd7467e 100644 --- a/source/blender/makesdna/DNA_space_types.h +++ b/source/blender/makesdna/DNA_space_types.h @@ -229,7 +229,7 @@ typedef struct SpaceImage { char dt_uv; /* UV draw type */ char sticky; /* sticky selection type */ char dt_uvstretch; - char around; + char pad; float xof, yof; /* user defined offset, image is centered */ float zoom, pad4; /* user defined zoom level */ diff --git a/source/blender/makesdna/DNA_userdef_types.h b/source/blender/makesdna/DNA_userdef_types.h index 771a7e43793..9d554c88a95 100644 --- a/source/blender/makesdna/DNA_userdef_types.h +++ b/source/blender/makesdna/DNA_userdef_types.h @@ -67,8 +67,7 @@ typedef struct uiFontStyle { short uifont_id; /* saved in file, 0 is default */ short points; /* actual size depends on 'global' dpi */ float kerning; /* kerning space between characters. */ - short overlap; /* check overlaped characters. */ - short pad; + float pad; short italic, bold; /* style hint */ short shadow; /* value is amount of pixels blur */ short shadx, shady; /* shadow offset in pixels */ @@ -124,11 +123,10 @@ typedef struct uiWidgetColors { typedef struct ThemeUI { /* Interface Elements (buttons, menus, icons) */ - uiWidgetColors wcol_regular, wcol_tool, wcol_text; - uiWidgetColors wcol_radio, wcol_option, wcol_toggle; + uiWidgetColors wcol_regular, wcol_tool, wcol_radio, wcol_text, wcol_option; uiWidgetColors wcol_num, wcol_numslider; uiWidgetColors wcol_menu, wcol_pulldown, wcol_menu_back, wcol_menu_item; - uiWidgetColors wcol_box, wcol_scroll; + uiWidgetColors wcol_box; char iconfile[80]; // FILE_MAXFILE length @@ -381,7 +379,7 @@ extern UserDef U; /* from blenkernel blender.c */ #define USER_ZOOM_TO_MOUSEPOS (1 << 20) #define USER_SHOW_FPS (1 << 21) #define USER_MMB_PASTE (1 << 22) -#define USER_MENUFIXEDORDER (1 << 23) +#define USER_DIRECTIONALORDER (1 << 23) /* Auto-Keying mode */ /* AUTOKEY_ON is a bitflag */ diff --git a/source/blender/makesdna/DNA_windowmanager_types.h b/source/blender/makesdna/DNA_windowmanager_types.h index e02d2984771..7d6b5ec8764 100644 --- a/source/blender/makesdna/DNA_windowmanager_types.h +++ b/source/blender/makesdna/DNA_windowmanager_types.h @@ -222,36 +222,5 @@ typedef enum wmRadialControlMode { WM_RADIALCONTROL_ANGLE } wmRadialControlMode; -/* ************** wmEvent ************************ */ -/* for read-only rna access, dont save this */ - -/* each event should have full modifier state */ -/* event comes from eventmanager and from keymap */ -typedef struct wmEvent { - struct wmEvent *next, *prev; - - short type; /* event code itself (short, is also in keymap) */ - short val; /* press, release, scrollvalue */ - short x, y; /* mouse pointer position, screen coord */ - short mval[2]; /* region mouse position, name convention pre 2.5 :) */ - short prevx, prevy; /* previous mouse pointer position */ - short unicode; /* future, ghost? */ - char ascii; /* from ghost */ - char pad; - - /* modifier states */ - short shift, ctrl, alt, oskey; /* oskey is apple or windowskey, value denotes order of pressed */ - short keymodifier; /* rawkey modifier */ - - /* keymap item, set by handler (weak?) */ - const char *keymap_idname; - - /* custom data */ - short custom; /* custom data type, stylus, 6dof, see wm_event_types.h */ - void *customdata; /* ascii, unicode, mouse coords, angles, vectors, dragdrop info */ - short customdatafree; - -} wmEvent; - #endif /* DNA_WINDOWMANAGER_TYPES_H */ diff --git a/source/blender/makesdna/intern/makesdna.c b/source/blender/makesdna/intern/makesdna.c index 91e9e617ea9..bf2f0f3900e 100644 --- a/source/blender/makesdna/intern/makesdna.c +++ b/source/blender/makesdna/intern/makesdna.c @@ -98,6 +98,7 @@ char *includefiles[] = { "DNA_object_force.h", "DNA_object_fluidsim.h", "DNA_world_types.h", + "DNA_radio_types.h", "DNA_scene_types.h", "DNA_view3d_types.h", "DNA_view2d_types.h", @@ -1123,6 +1124,7 @@ int main(int argc, char ** argv) #include "DNA_object_force.h" #include "DNA_object_fluidsim.h" #include "DNA_world_types.h" +#include "DNA_radio_types.h" #include "DNA_scene_types.h" #include "DNA_view3d_types.h" #include "DNA_view2d_types.h" diff --git a/source/blender/makesrna/Makefile b/source/blender/makesrna/Makefile index bed3e85550d..25625af57a6 100644 --- a/source/blender/makesrna/Makefile +++ b/source/blender/makesrna/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 21247 2009-06-29 21:50:53Z jaguarandi $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/makesrna/RNA_access.h b/source/blender/makesrna/RNA_access.h index 1f856062533..c1a659fee9b 100644 --- a/source/blender/makesrna/RNA_access.h +++ b/source/blender/makesrna/RNA_access.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: RNA_access.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -172,7 +172,6 @@ extern StructRNA RNA_EnvironmentMap; extern StructRNA RNA_EnvironmentMapTexture; extern StructRNA RNA_ExplodeModifier; extern StructRNA RNA_ExpressionController; -extern StructRNA RNA_Event; extern StructRNA RNA_FCurve; extern StructRNA RNA_FModifier; extern StructRNA RNA_FModifierCycles; @@ -514,8 +513,6 @@ const struct ListBase *RNA_struct_defined_properties(StructRNA *srna); FunctionRNA *RNA_struct_find_function(PointerRNA *ptr, const char *identifier); const struct ListBase *RNA_struct_defined_functions(StructRNA *srna); -char *RNA_struct_name_get_alloc(PointerRNA *ptr, char *fixedbuf, int fixedlen); - /* Properties * * Access to struct properties. All this works with RNA pointers rather than @@ -544,9 +541,6 @@ void RNA_property_int_ui_range(PointerRNA *ptr, PropertyRNA *prop, int *softmin, void RNA_property_float_range(PointerRNA *ptr, PropertyRNA *prop, float *hardmin, float *hardmax); void RNA_property_float_ui_range(PointerRNA *ptr, PropertyRNA *prop, float *softmin, float *softmax, float *step, float *precision); -int RNA_enum_identifier(const EnumPropertyItem *item, const int value, const char **identifier); -int RNA_enum_name(const EnumPropertyItem *item, const int value, const char **name); - void RNA_property_enum_items(PointerRNA *ptr, PropertyRNA *prop, const EnumPropertyItem **item, int *totitem); int RNA_property_enum_value(PointerRNA *ptr, PropertyRNA *prop, const char *identifier, int *value); int RNA_property_enum_identifier(PointerRNA *ptr, PropertyRNA *prop, const int value, const char **identifier); @@ -600,11 +594,6 @@ int RNA_property_collection_length(PointerRNA *ptr, PropertyRNA *prop); int RNA_property_collection_lookup_int(PointerRNA *ptr, PropertyRNA *prop, int key, PointerRNA *r_ptr); int RNA_property_collection_lookup_string(PointerRNA *ptr, PropertyRNA *prop, const char *key, PointerRNA *r_ptr); -/* efficient functions to set properties for arrays */ -int RNA_property_collection_raw_array(PointerRNA *ptr, PropertyRNA *prop, PropertyRNA *itemprop, RawArray *array); -int RNA_property_collection_raw_get(struct ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, char *propname, void *array, RawPropertyType type, int len); -int RNA_property_collection_raw_set(struct ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, char *propname, void *array, RawPropertyType type, int len); - /* to create ID property groups */ void RNA_property_pointer_add(PointerRNA *ptr, PropertyRNA *prop); void RNA_property_pointer_remove(PointerRNA *ptr, PropertyRNA *prop); @@ -700,28 +689,6 @@ void RNA_collection_clear(PointerRNA *ptr, const char *name); RNA_property_collection_end(&rna_macro_iter); \ } -#define RNA_PROP_BEGIN(sptr, itemptr, prop) \ - { \ - CollectionPropertyIterator rna_macro_iter; \ - for(RNA_property_collection_begin(sptr, prop, &rna_macro_iter); rna_macro_iter.valid; RNA_property_collection_next(&rna_macro_iter)) { \ - PointerRNA itemptr= rna_macro_iter.ptr; - -#define RNA_PROP_END \ - } \ - RNA_property_collection_end(&rna_macro_iter); \ - } - -#define RNA_STRUCT_BEGIN(sptr, prop) \ - { \ - CollectionPropertyIterator rna_macro_iter; \ - for(RNA_property_collection_begin(sptr, RNA_struct_iterator_property(sptr->type), &rna_macro_iter); rna_macro_iter.valid; RNA_property_collection_next(&rna_macro_iter)) { \ - PropertyRNA *prop= rna_macro_iter.ptr.data; - -#define RNA_STRUCT_END \ - } \ - RNA_property_collection_end(&rna_macro_iter); \ - } - /* check if the idproperty exists, for operators */ int RNA_property_is_set(PointerRNA *ptr, const char *name); diff --git a/source/blender/makesrna/RNA_define.h b/source/blender/makesrna/RNA_define.h index 85a148be2e2..91669616d89 100644 --- a/source/blender/makesrna/RNA_define.h +++ b/source/blender/makesrna/RNA_define.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: RNA_define.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -80,7 +80,7 @@ PropertyRNA *RNA_def_string(StructOrFunctionRNA *cont, const char *identifier, c PropertyRNA *RNA_def_string_file_path(StructOrFunctionRNA *cont, const char *identifier, const char *default_value, int maxlen, const char *ui_name, const char *ui_description); PropertyRNA *RNA_def_string_dir_path(StructOrFunctionRNA *cont, const char *identifier, const char *default_value, int maxlen, const char *ui_name, const char *ui_description); -PropertyRNA *RNA_def_enum(StructOrFunctionRNA *cont, const char *identifier, const EnumPropertyItem *items, int default_value, const char *ui_name, const char *ui_description); +PropertyRNA *RNA_def_enum(StructOrFunctionRNA *cont, const char *identifier, EnumPropertyItem *items, int default_value, const char *ui_name, const char *ui_description); PropertyRNA *RNA_def_float(StructOrFunctionRNA *cont, const char *identifier, float default_value, float hardmin, float hardmax, const char *ui_name, const char *ui_description, float softmin, float softmax); PropertyRNA *RNA_def_float_vector(StructOrFunctionRNA *cont, const char *identifier, int len, const float *default_value, float hardmin, float hardmax, const char *ui_name, const char *ui_description, float softmin, float softmax); diff --git a/source/blender/makesrna/RNA_enum_types.h b/source/blender/makesrna/RNA_enum_types.h index 276f421c586..841b397f276 100644 --- a/source/blender/makesrna/RNA_enum_types.h +++ b/source/blender/makesrna/RNA_enum_types.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: RNA_enum_types.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -40,9 +40,6 @@ extern EnumPropertyItem beztriple_interpolation_mode_items[]; extern EnumPropertyItem fmodifier_type_items[]; -extern EnumPropertyItem event_value_items[]; -extern EnumPropertyItem event_type_items[]; - #endif /* RNA_ENUM_TYPES */ diff --git a/source/blender/makesrna/RNA_types.h b/source/blender/makesrna/RNA_types.h index 923191cba78..a0fa2cc3344 100644 --- a/source/blender/makesrna/RNA_types.h +++ b/source/blender/makesrna/RNA_types.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: RNA_types.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -110,9 +110,7 @@ typedef enum PropertyFlag { PROP_BUILTIN = 128, PROP_EXPORT = 256, PROP_RUNTIME = 512, - PROP_IDPROPERTY = 1024, - PROP_RAW_ACCESS = 8192, - PROP_RAW_ARRAY = 16384, + PROP_IDPROPERTY = 1024 } PropertyFlag; typedef struct CollectionPropertyIterator { @@ -134,21 +132,6 @@ typedef struct CollectionPointerLink { PointerRNA ptr; } CollectionPointerLink; -typedef enum RawPropertyType { - PROP_RAW_CHAR, - PROP_RAW_SHORT, - PROP_RAW_INT, - PROP_RAW_FLOAT, - PROP_RAW_DOUBLE -} RawPropertyType; - -typedef struct RawArray { - void *array; - RawPropertyType type; - int len; - int stride; -} RawArray; - /* Iterator Utility */ typedef struct EnumPropertyItem { diff --git a/source/blender/makesrna/intern/Makefile b/source/blender/makesrna/intern/Makefile index 1694e55ed4c..03f75f0bea6 100644 --- a/source/blender/makesrna/intern/Makefile +++ b/source/blender/makesrna/intern/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 13161 2008-01-07 19:13:47Z hos $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/makesrna/intern/makesrna.c b/source/blender/makesrna/intern/makesrna.c index c42bc866f99..1db61a842e5 100644 --- a/source/blender/makesrna/intern/makesrna.c +++ b/source/blender/makesrna/intern/makesrna.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: makesrna.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -36,7 +36,7 @@ #include "rna_internal.h" -#define RNA_VERSION_DATE "$Id$" +#define RNA_VERSION_DATE "$Id: makesrna.c 21247 2009-06-29 21:50:53Z jaguarandi $" #ifdef _WIN32 #ifndef snprintf @@ -248,7 +248,8 @@ static const char *rna_parameter_type_name(PropertyRNA *parm) return rna_find_dna_type((const char *)pparm->type); } case PROP_COLLECTION: { - return "ListBase"; + CollectionPropertyRNA *cparm= (CollectionPropertyRNA*)parm; + return rna_find_dna_type((const char *)cparm->type); } default: return "<error, no type specified>"; @@ -762,42 +763,6 @@ static char *rna_def_property_end_func(FILE *f, StructRNA *srna, PropertyRNA *pr return func; } -static void rna_set_raw_property(PropertyDefRNA *dp, PropertyRNA *prop) -{ - if(dp->dnapointerlevel != 0) - return; - if(!dp->dnatype || !dp->dnaname || !dp->dnastructname) - return; - - if(strcmp(dp->dnatype, "char") == 0) { - prop->rawtype= PROP_RAW_CHAR; - prop->flag |= PROP_RAW_ACCESS; - } - else if(strcmp(dp->dnatype, "short") == 0) { - prop->rawtype= PROP_RAW_SHORT; - prop->flag |= PROP_RAW_ACCESS; - } - else if(strcmp(dp->dnatype, "int") == 0) { - prop->rawtype= PROP_RAW_INT; - prop->flag |= PROP_RAW_ACCESS; - } - else if(strcmp(dp->dnatype, "float") == 0) { - prop->rawtype= PROP_RAW_FLOAT; - prop->flag |= PROP_RAW_ACCESS; - } - else if(strcmp(dp->dnatype, "double") == 0) { - prop->rawtype= PROP_RAW_DOUBLE; - prop->flag |= PROP_RAW_ACCESS; - } -} - -static void rna_set_raw_offset(FILE *f, StructRNA *srna, PropertyRNA *prop) -{ - PropertyDefRNA *dp= rna_find_struct_property_def(srna, prop); - - fprintf(f, "\toffsetof(%s, %s), %d", dp->dnastructname, dp->dnaname, prop->rawtype); -} - static void rna_def_property_funcs(FILE *f, StructRNA *srna, PropertyDefRNA *dp) { PropertyRNA *prop; @@ -809,9 +774,6 @@ static void rna_def_property_funcs(FILE *f, StructRNA *srna, PropertyDefRNA *dp) BooleanPropertyRNA *bprop= (BooleanPropertyRNA*)prop; if(!prop->arraylength) { - if(!bprop->get && !bprop->set && !dp->booleanbit) - rna_set_raw_property(dp, prop); - bprop->get= (void*)rna_def_property_get_func(f, srna, prop, dp, (char*)bprop->get); bprop->set= (void*)rna_def_property_set_func(f, srna, prop, dp, (char*)bprop->set); } @@ -825,16 +787,10 @@ static void rna_def_property_funcs(FILE *f, StructRNA *srna, PropertyDefRNA *dp) IntPropertyRNA *iprop= (IntPropertyRNA*)prop; if(!prop->arraylength) { - if(!iprop->get && !iprop->set) - rna_set_raw_property(dp, prop); - iprop->get= (void*)rna_def_property_get_func(f, srna, prop, dp, (char*)iprop->get); iprop->set= (void*)rna_def_property_set_func(f, srna, prop, dp, (char*)iprop->set); } else { - if(!iprop->getarray && !iprop->setarray) - rna_set_raw_property(dp, prop); - iprop->getarray= (void*)rna_def_property_get_func(f, srna, prop, dp, (char*)iprop->getarray); iprop->setarray= (void*)rna_def_property_set_func(f, srna, prop, dp, (char*)iprop->setarray); } @@ -844,16 +800,10 @@ static void rna_def_property_funcs(FILE *f, StructRNA *srna, PropertyDefRNA *dp) FloatPropertyRNA *fprop= (FloatPropertyRNA*)prop; if(!prop->arraylength) { - if(!fprop->get && !fprop->set) - rna_set_raw_property(dp, prop); - fprop->get= (void*)rna_def_property_get_func(f, srna, prop, dp, (char*)fprop->get); fprop->set= (void*)rna_def_property_set_func(f, srna, prop, dp, (char*)fprop->set); } else { - if(!fprop->getarray && !fprop->setarray) - rna_set_raw_property(dp, prop); - fprop->getarray= (void*)rna_def_property_get_func(f, srna, prop, dp, (char*)fprop->getarray); fprop->setarray= (void*)rna_def_property_set_func(f, srna, prop, dp, (char*)fprop->setarray); } @@ -892,13 +842,6 @@ static void rna_def_property_funcs(FILE *f, StructRNA *srna, PropertyDefRNA *dp) else if(dp->dnalengthname || dp->dnalengthfixed) cprop->length= (void*)rna_def_property_length_func(f, srna, prop, dp, (char*)cprop->length); - /* test if we can allow raw array access, if it is using our standard - * array get/next function, we can be sure it is an actual array */ - if(cprop->next && cprop->get) - if(strcmp((char*)cprop->next, "rna_iterator_array_next") == 0 && - strcmp((char*)cprop->get, "rna_iterator_array_get") == 0) - prop->flag |= PROP_RAW_ARRAY; - cprop->get= (void*)rna_def_property_get_func(f, srna, prop, dp, (char*)cprop->get); cprop->begin= (void*)rna_def_property_begin_func(f, srna, prop, dp, (char*)cprop->begin); cprop->next= (void*)rna_def_property_next_func(f, srna, prop, dp, (char*)cprop->next); @@ -1173,11 +1116,9 @@ static void rna_def_function_funcs(FILE *f, StructDefRNA *dsrna, FunctionDefRNA funcname= rna_alloc_function_name(srna->identifier, func->identifier, "call"); - /* function definition */ fprintf(f, "void %s(bContext *C, ReportList *reports, PointerRNA *_ptr, ParameterList *_parms)", funcname); fprintf(f, "\n{\n"); - /* variable definitions */ if((func->flag & FUNC_NO_SELF)==0) { if(dsrna->dnaname) fprintf(f, "\tstruct %s *_self;\n", dsrna->dnaname); else fprintf(f, "\tstruct %s *_self;\n", srna->identifier); @@ -1194,7 +1135,6 @@ static void rna_def_function_funcs(FILE *f, StructDefRNA *dsrna, FunctionDefRNA fprintf(f, ";\n"); fprintf(f, "\t\n"); - /* assign self */ if((func->flag & FUNC_NO_SELF)==0) { if(dsrna->dnaname) fprintf(f, "\t_self= (struct %s *)_ptr->data;\n", dsrna->dnaname); else fprintf(f, "\t_self= (struct %s *)_ptr->data;\n", srna->identifier); @@ -1465,7 +1405,6 @@ static void rna_generate_static_parameter_prototypes(BlenderRNA *brna, StructRNA dsrna= rna_find_struct_def(srna); func= dfunc->func; - /* return type */ for(dparm= dfunc->cont.properties.first; dparm; dparm= dparm->next) { if(dparm->prop==func->ret) { if(dparm->prop->arraylength) @@ -1479,16 +1418,13 @@ static void rna_generate_static_parameter_prototypes(BlenderRNA *brna, StructRNA } } - /* void if nothing to return */ if(!dparm) fprintf(f, "void "); - /* function name */ fprintf(f, "%s(", dfunc->call); first= 1; - /* self, context and reports parameters */ if((func->flag & FUNC_NO_SELF)==0) { if(dsrna->dnaname) fprintf(f, "struct %s *_self", dsrna->dnaname); else fprintf(f, "struct %s *_self", srna->identifier); @@ -1507,7 +1443,6 @@ static void rna_generate_static_parameter_prototypes(BlenderRNA *brna, StructRNA fprintf(f, "ReportList *reports"); } - /* defined parameters */ for(dparm= dfunc->cont.properties.first; dparm; dparm= dparm->next) { if(dparm->prop==func->ret) continue; @@ -1596,7 +1531,7 @@ static void rna_generate_property(FILE *f, StructRNA *srna, const char *nest, Pr DefRNA.error= 1; } break; - } + } case PROP_BOOLEAN: { BooleanPropertyRNA *bprop= (BooleanPropertyRNA*)prop; unsigned int i; @@ -1616,7 +1551,7 @@ static void rna_generate_property(FILE *f, StructRNA *srna, const char *nest, Pr fprintf(f, "};\n\n"); } break; - } + } case PROP_INT: { IntPropertyRNA *iprop= (IntPropertyRNA*)prop; unsigned int i; @@ -1636,7 +1571,7 @@ static void rna_generate_property(FILE *f, StructRNA *srna, const char *nest, Pr fprintf(f, "};\n\n"); } break; - } + } case PROP_FLOAT: { FloatPropertyRNA *fprop= (FloatPropertyRNA*)prop; unsigned int i; @@ -1656,7 +1591,7 @@ static void rna_generate_property(FILE *f, StructRNA *srna, const char *nest, Pr fprintf(f, "};\n\n"); } break; - } + } default: break; } @@ -1671,14 +1606,10 @@ static void rna_generate_property(FILE *f, StructRNA *srna, const char *nest, Pr rna_print_c_string(f, prop->identifier); fprintf(f, ", %d, ", prop->flag); rna_print_c_string(f, prop->name); fprintf(f, ",\n\t"); - rna_print_c_string(f, prop->description); fprintf(f, ",\n\t"); - fprintf(f, "%d,\n", prop->icon); + rna_print_c_string(f, prop->description); fprintf(f, ",\n"); + fprintf(f, "%d, ", prop->icon); fprintf(f, "\t%s, %s, %d,\n", rna_property_typename(prop->type), rna_property_subtypename(prop->subtype), prop->arraylength); - fprintf(f, "\t%s, %d, %s,\n", rna_function_string(prop->update), prop->noteflag, rna_function_string(prop->editable)); - - if(prop->flag & PROP_RAW_ACCESS) rna_set_raw_offset(f, srna, prop); - else fprintf(f, "\t0, 0"); - fprintf(f, "},\n"); + fprintf(f, "\t%s, %d, %s},\n", rna_function_string(prop->update), prop->noteflag, rna_function_string(prop->editable)); switch(prop->type) { case PROP_BOOLEAN: { @@ -1687,7 +1618,7 @@ static void rna_generate_property(FILE *f, StructRNA *srna, const char *nest, Pr if(prop->arraylength) fprintf(f, "rna_%s%s_%s_default\n", srna->identifier, strnest, prop->identifier); else fprintf(f, "NULL\n"); break; - } + } case PROP_INT: { IntPropertyRNA *iprop= (IntPropertyRNA*)prop; fprintf(f, "\t%s, %s, %s, %s, %s,\n\t", rna_function_string(iprop->get), rna_function_string(iprop->set), rna_function_string(iprop->getarray), rna_function_string(iprop->setarray), rna_function_string(iprop->range)); @@ -1700,7 +1631,7 @@ static void rna_generate_property(FILE *f, StructRNA *srna, const char *nest, Pr if(prop->arraylength) fprintf(f, "rna_%s%s_%s_default\n", srna->identifier, strnest, prop->identifier); else fprintf(f, "NULL\n"); break; - } + } case PROP_FLOAT: { FloatPropertyRNA *fprop= (FloatPropertyRNA*)prop; fprintf(f, "\t%s, %s, %s, %s, %s, ", rna_function_string(fprop->get), rna_function_string(fprop->set), rna_function_string(fprop->getarray), rna_function_string(fprop->setarray), rna_function_string(fprop->range)); @@ -1714,13 +1645,13 @@ static void rna_generate_property(FILE *f, StructRNA *srna, const char *nest, Pr if(prop->arraylength) fprintf(f, "rna_%s%s_%s_default\n", srna->identifier, strnest, prop->identifier); else fprintf(f, "NULL\n"); break; - } + } case PROP_STRING: { StringPropertyRNA *sprop= (StringPropertyRNA*)prop; fprintf(f, "\t%s, %s, %s, %d, ", rna_function_string(sprop->get), rna_function_string(sprop->length), rna_function_string(sprop->set), sprop->maxlength); rna_print_c_string(f, sprop->defaultvalue); fprintf(f, "\n"); break; - } + } case PROP_ENUM: { EnumPropertyRNA *eprop= (EnumPropertyRNA*)prop; fprintf(f, "\t%s, %s, %s, ", rna_function_string(eprop->get), rna_function_string(eprop->set), rna_function_string(eprop->itemf)); @@ -1730,14 +1661,14 @@ static void rna_generate_property(FILE *f, StructRNA *srna, const char *nest, Pr fprintf(f, "NULL, "); fprintf(f, "%d, %d\n", eprop->totitem, eprop->defaultvalue); break; - } + } case PROP_POINTER: { PointerPropertyRNA *pprop= (PointerPropertyRNA*)prop; fprintf(f, "\t%s, %s, %s, ", rna_function_string(pprop->get), rna_function_string(pprop->set), rna_function_string(pprop->typef)); if(pprop->type) fprintf(f, "&RNA_%s\n", (char*)pprop->type); else fprintf(f, "NULL\n"); break; - } + } case PROP_COLLECTION: { CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)prop; fprintf(f, "\t%s, %s, %s, %s, %s, %s, %s, ", rna_function_string(cprop->begin), rna_function_string(cprop->next), rna_function_string(cprop->end), rna_function_string(cprop->get), rna_function_string(cprop->length), rna_function_string(cprop->lookupint), rna_function_string(cprop->lookupstring)); @@ -1922,6 +1853,7 @@ RNAProcessItem PROCESS_ITEMS[]= { {"rna_particle.c", NULL, RNA_def_particle}, {"rna_pose.c", NULL, RNA_def_pose}, {"rna_property.c", NULL, RNA_def_gameproperty}, + {"rna_radio.c", NULL, RNA_def_radio}, {"rna_scene.c", NULL, RNA_def_scene}, {"rna_screen.c", NULL, RNA_def_screen}, {"rna_scriptlink.c", NULL, RNA_def_scriptlink}, @@ -1952,7 +1884,6 @@ static void rna_generate(BlenderRNA *brna, FILE *f, char *filename, char *api_fi fprintf(f, "#include <float.h>\n"); fprintf(f, "#include <limits.h>\n"); fprintf(f, "#include <string.h>\n\n"); - fprintf(f, "#include <stddef.h>\n\n"); fprintf(f, "#include \"DNA_ID.h\"\n"); diff --git a/source/blender/makesrna/intern/rna_ID.c b/source/blender/makesrna/intern/rna_ID.c index 7d8bab8bee8..e70cd6ff8d3 100644 --- a/source/blender/makesrna/intern/rna_ID.c +++ b/source/blender/makesrna/intern/rna_ID.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_ID.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_access.c b/source/blender/makesrna/intern/rna_access.c index d3e4780c7fd..3073029d9b4 100644 --- a/source/blender/makesrna/intern/rna_access.c +++ b/source/blender/makesrna/intern/rna_access.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_access.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -426,16 +426,23 @@ PropertyRNA *RNA_struct_find_property(PointerRNA *ptr, const char *identifier) /* Find the property which uses the given nested struct */ PropertyRNA *RNA_struct_find_nested(PointerRNA *ptr, StructRNA *srna) { - PropertyRNA *prop= NULL; + CollectionPropertyIterator iter; + PropertyRNA *iterprop, *prop; + int i = 0; + + iterprop= RNA_struct_iterator_property(ptr->type); + RNA_property_collection_begin(ptr, iterprop, &iter); + prop= NULL; - RNA_STRUCT_BEGIN(ptr, iprop) { + for(; iter.valid; RNA_property_collection_next(&iter), i++) { /* This assumes that there can only be one user of this nested struct */ - if (RNA_property_pointer_type(ptr, iprop) == srna) { - prop= iprop; + if (RNA_property_pointer_type(ptr, iter.ptr.data) == srna) { + prop= iter.ptr.data; break; } } - RNA_PROP_END; + + RNA_property_collection_end(&iter); return prop; } @@ -448,21 +455,25 @@ const struct ListBase *RNA_struct_defined_properties(StructRNA *srna) FunctionRNA *RNA_struct_find_function(PointerRNA *ptr, const char *identifier) { PointerRNA tptr; + CollectionPropertyIterator iter; PropertyRNA *iterprop; FunctionRNA *func; + int i = 0; RNA_pointer_create(NULL, &RNA_Struct, ptr->type, &tptr); iterprop= RNA_struct_find_property(&tptr, "functions"); + RNA_property_collection_begin(&tptr, iterprop, &iter); func= NULL; - RNA_PROP_BEGIN(&tptr, funcptr, iterprop) { - if(strcmp(identifier, RNA_function_identifier(funcptr.data)) == 0) { - func= funcptr.data; + for(; iter.valid; RNA_property_collection_next(&iter), i++) { + if(strcmp(identifier, RNA_function_identifier(iter.ptr.data)) == 0) { + func= iter.ptr.data; break; } } - RNA_PROP_END; + + RNA_property_collection_end(&iter); return func; } @@ -507,16 +518,6 @@ void RNA_struct_blender_type_set(StructRNA *srna, void *blender_type) srna->blender_type= blender_type; } -char *RNA_struct_name_get_alloc(PointerRNA *ptr, char *fixedbuf, int fixedlen) -{ - PropertyRNA *nameprop; - - if(ptr->data && (nameprop = RNA_struct_name_property(ptr->type))) - return RNA_property_string_get_alloc(ptr, nameprop, fixedbuf, fixedlen); - - return NULL; -} - /* Property Information */ const char *RNA_property_identifier(PropertyRNA *prop) @@ -642,27 +643,25 @@ void RNA_property_enum_items(PointerRNA *ptr, PropertyRNA *prop, const EnumPrope if(eprop->itemf) { *item= eprop->itemf(ptr); - if(totitem) { - for(tot=0; (*item)[tot].identifier; tot++); - *totitem= tot; - } + for(tot=0; (*item)[tot].identifier; tot++); + *totitem= tot; } else { *item= eprop->item; - if(totitem) - *totitem= eprop->totitem; + *totitem= eprop->totitem; } } int RNA_property_enum_value(PointerRNA *ptr, PropertyRNA *prop, const char *identifier, int *value) { const EnumPropertyItem *item; + int totitem, i; - RNA_property_enum_items(ptr, prop, &item, NULL); + RNA_property_enum_items(ptr, prop, &item, &totitem); - for(; item->identifier; item++) { - if(strcmp(item->identifier, identifier)==0) { - *value = item->value; + for(i=0; i<totitem; i++) { + if(strcmp(item[i].identifier, identifier)==0) { + *value = item[i].value; return 1; } } @@ -670,34 +669,21 @@ int RNA_property_enum_value(PointerRNA *ptr, PropertyRNA *prop, const char *iden return 0; } -int RNA_enum_identifier(const EnumPropertyItem *item, const int value, const char **identifier) -{ - for (; item->identifier; item++) { - if(item->value==value) { - *identifier = item->identifier; - return 1; - } - } - return 0; -} - -int RNA_enum_name(const EnumPropertyItem *item, const int value, const char **name) -{ - for (; item->identifier; item++) { - if(item->value==value) { - *name = item->name; +int RNA_property_enum_identifier(PointerRNA *ptr, PropertyRNA *prop, const int value, const char **identifier) +{ + const EnumPropertyItem *item; + int totitem, i; + + RNA_property_enum_items(ptr, prop, &item, &totitem); + + for(i=0; i<totitem; i++) { + if(item[i].value==value) { + *identifier = item[i].identifier; return 1; } } - return 0; -} - -int RNA_property_enum_identifier(PointerRNA *ptr, PropertyRNA *prop, const int value, const char **identifier) -{ - const EnumPropertyItem *item= NULL; - RNA_property_enum_items(ptr, prop, &item, NULL); - return RNA_enum_identifier(item, value, identifier); + return 0; } const char *RNA_property_ui_name(PropertyRNA *prop) @@ -1522,313 +1508,6 @@ int RNA_property_collection_lookup_string(PointerRNA *ptr, PropertyRNA *prop, co } } -int RNA_property_collection_raw_array(PointerRNA *ptr, PropertyRNA *prop, PropertyRNA *itemprop, RawArray *array) -{ - CollectionPropertyIterator iter; - ArrayIterator *internal; - char *arrayp; - - if(!(prop->flag & PROP_RAW_ARRAY) || !(itemprop->flag & PROP_RAW_ACCESS)) - return 0; - - RNA_property_collection_begin(ptr, prop, &iter); - - if(iter.valid) { - /* get data from array iterator and item property */ - internal= iter.internal; - arrayp= (iter.valid)? iter.ptr.data: NULL; - - if(internal->skip || !RNA_property_editable(&iter.ptr, itemprop)) { - /* we might skip some items, so it's not a proper array */ - RNA_property_collection_end(&iter); - return 0; - } - - array->array= arrayp + itemprop->rawoffset; - array->stride= internal->itemsize; - array->len= ((char*)internal->endptr - arrayp)/internal->itemsize; - array->type= itemprop->rawtype; - } - else - memset(array, 0, sizeof(RawArray)); - - RNA_property_collection_end(&iter); - - return 1; -} - -#define RAW_GET(dtype, var, raw, a) \ -{ \ - switch(raw.type) { \ - case PROP_RAW_CHAR: var = (dtype)((char*)raw.array)[a]; break; \ - case PROP_RAW_SHORT: var = (dtype)((short*)raw.array)[a]; break; \ - case PROP_RAW_INT: var = (dtype)((int*)raw.array)[a]; break; \ - case PROP_RAW_FLOAT: var = (dtype)((float*)raw.array)[a]; break; \ - case PROP_RAW_DOUBLE: var = (dtype)((double*)raw.array)[a]; break; \ - default: var = (dtype)0; \ - } \ -} - -#define RAW_SET(dtype, raw, a, var) \ -{ \ - switch(raw.type) { \ - case PROP_RAW_CHAR: ((char*)raw.array)[a] = (char)var; break; \ - case PROP_RAW_SHORT: ((short*)raw.array)[a] = (short)var; break; \ - case PROP_RAW_INT: ((int*)raw.array)[a] = (int)var; break; \ - case PROP_RAW_FLOAT: ((float*)raw.array)[a] = (float)var; break; \ - case PROP_RAW_DOUBLE: ((double*)raw.array)[a] = (double)var; break; \ - } \ -} - -static int rna_raw_access(ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, char *propname, void *inarray, RawPropertyType intype, int inlen, int set) -{ - StructRNA *ptype; - PointerRNA itemptr; - PropertyRNA *itemprop, *iprop; - PropertyType itemtype; - RawArray in; - int itemlen= 0; - - /* initialize in array, stride assumed 0 in following code */ - in.array= inarray; - in.type= intype; - in.len= inlen; - in.stride= 0; - - ptype= RNA_property_pointer_type(ptr, prop); - - /* try to get item property pointer */ - RNA_pointer_create(NULL, ptype, NULL, &itemptr); - itemprop= RNA_struct_find_property(&itemptr, propname); - - if(itemprop) { - /* we have item property pointer */ - RawArray out; - - /* check type */ - itemtype= RNA_property_type(itemprop); - - if(!ELEM3(itemtype, PROP_BOOLEAN, PROP_INT, PROP_FLOAT)) { - BKE_report(reports, RPT_ERROR, "Only boolean, int and float properties supported."); - return 0; - } - - /* check item array */ - itemlen= RNA_property_array_length(itemprop); - - /* try to access as raw array */ - if(RNA_property_collection_raw_array(ptr, prop, itemprop, &out)) { - if(in.len != itemlen*out.len) { - BKE_reportf(reports, RPT_ERROR, "Array length mismatch (expected %d, got %d).", out.len*itemlen, in.len); - return 0; - } - - /* matching raw types */ - if(out.type == in.type) { - void *inp= in.array; - void *outp= out.array; - int a, size; - - itemlen= (itemlen == 0)? 1: itemlen; - - switch(out.type) { - case PROP_RAW_CHAR: size= sizeof(char)*itemlen; break; - case PROP_RAW_SHORT: size= sizeof(short)*itemlen; break; - case PROP_RAW_INT: size= sizeof(int)*itemlen; break; - case PROP_RAW_FLOAT: size= sizeof(float)*itemlen; break; - case PROP_RAW_DOUBLE: size= sizeof(double)*itemlen; break; - } - - for(a=0; a<out.len; a++) { - if(set) memcpy(outp, inp, size); - else memcpy(inp, outp, size); - - inp= (char*)inp + size; - outp= (char*)outp + out.stride; - } - - return 1; - } - - /* could also be faster with non-matching types, - * for now we just do slower loop .. */ - } - } - - { - void *tmparray= NULL; - int tmplen= 0; - int err= 0, j, a= 0; - - /* no item property pointer, can still be id property, or - * property of a type derived from the collection pointer type */ - RNA_PROP_BEGIN(ptr, itemptr, prop) { - if(itemptr.data) { - if(itemprop) { - /* we got the property already */ - iprop= itemprop; - } - else { - /* not yet, look it up and verify if it is valid */ - iprop= RNA_struct_find_property(&itemptr, propname); - - if(iprop) { - itemlen= RNA_property_array_length(iprop); - itemtype= RNA_property_type(iprop); - } - else { - BKE_reportf(reports, RPT_ERROR, "Property named %s not found.", propname); - err= 1; - break; - } - - if(!ELEM3(itemtype, PROP_BOOLEAN, PROP_INT, PROP_FLOAT)) { - BKE_report(reports, RPT_ERROR, "Only boolean, int and float properties supported."); - err= 1; - break; - } - } - - /* editable check */ - if(RNA_property_editable(&itemptr, iprop)) { - if(a+itemlen > in.len) { - BKE_reportf(reports, RPT_ERROR, "Array length mismatch (got %d, expected more).", in.len); - err= 1; - break; - } - - if(itemlen == 0) { - /* handle conversions */ - if(set) { - switch(itemtype) { - case PROP_BOOLEAN: { - int b; - RAW_GET(int, b, in, a); - RNA_property_boolean_set(&itemptr, iprop, b); - break; - } - case PROP_INT: { - int i; - RAW_GET(int, i, in, a); - RNA_property_int_set(&itemptr, iprop, i); - break; - } - case PROP_FLOAT: { - float f; - RAW_GET(float, f, in, a); - RNA_property_float_set(&itemptr, iprop, f); - break; - } - default: - break; - } - } - else { - switch(itemtype) { - case PROP_BOOLEAN: { - int b= RNA_property_boolean_get(&itemptr, iprop); - RAW_SET(int, in, a, b); - break; - } - case PROP_INT: { - int i= RNA_property_int_get(&itemptr, iprop); - RAW_SET(int, in, a, i); - break; - } - case PROP_FLOAT: { - float f= RNA_property_float_get(&itemptr, iprop); - RAW_SET(float, in, a, f); - break; - } - default: - break; - } - } - a++; - } - else { - /* allocate temporary array if needed */ - if(tmparray && tmplen != itemlen) { - MEM_freeN(tmparray); - tmparray= NULL; - } - if(!tmparray) { - tmparray= MEM_callocN(sizeof(float)*itemlen, "RNA tmparray\n"); - tmplen= itemlen; - } - - /* handle conversions */ - if(set) { - switch(itemtype) { - case PROP_BOOLEAN: { - for(j=0; j<itemlen; j++, a++) - RAW_GET(int, ((int*)tmparray)[j], in, a); - RNA_property_boolean_set_array(&itemptr, iprop, tmparray); - break; - } - case PROP_INT: { - for(j=0; j<itemlen; j++, a++) - RAW_GET(int, ((int*)tmparray)[j], in, a); - RNA_property_int_set_array(&itemptr, iprop, tmparray); - break; - } - case PROP_FLOAT: { - for(j=0; j<itemlen; j++, a++) - RAW_GET(float, ((float*)tmparray)[j], in, a); - RNA_property_float_set_array(&itemptr, iprop, tmparray); - break; - } - default: - break; - } - } - else { - switch(itemtype) { - case PROP_BOOLEAN: { - RNA_property_boolean_get_array(&itemptr, iprop, tmparray); - for(j=0; j<itemlen; j++, a++) - RAW_SET(int, in, a, ((int*)tmparray)[j]); - break; - } - case PROP_INT: { - RNA_property_int_get_array(&itemptr, iprop, tmparray); - for(j=0; j<itemlen; j++, a++) - RAW_SET(int, in, a, ((int*)tmparray)[j]); - break; - } - case PROP_FLOAT: { - RNA_property_float_get_array(&itemptr, iprop, tmparray); - for(j=0; j<itemlen; j++, a++) - RAW_SET(float, in, a, ((float*)tmparray)[j]); - break; - } - default: - break; - } - } - } - } - } - } - RNA_PROP_END; - - if(tmparray) - MEM_freeN(tmparray); - - return !err; - } -} - -int RNA_property_collection_raw_get(ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, char *propname, void *array, RawPropertyType type, int len) -{ - return rna_raw_access(reports, ptr, prop, propname, array, type, len, 0); -} - -int RNA_property_collection_raw_set(ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, char *propname, void *array, RawPropertyType type, int len) -{ - return rna_raw_access(reports, ptr, prop, propname, array, type, len, 1); -} - /* Standard iterator functions */ void rna_iterator_listbase_begin(CollectionPropertyIterator *iter, ListBase *lb, IteratorSkipFunc skip) @@ -2373,13 +2052,14 @@ int RNA_enum_is_equal(PointerRNA *ptr, const char *name, const char *enumname) { PropertyRNA *prop= RNA_struct_find_property(ptr, name); const EnumPropertyItem *item; + int a, totitem; if(prop) { - RNA_property_enum_items(ptr, prop, &item, NULL); + RNA_property_enum_items(ptr, prop, &item, &totitem); - for(; item->identifier; item++) - if(strcmp(item->identifier, enumname) == 0) - return (item->value == RNA_property_enum_get(ptr, prop)); + for(a=0; a<totitem; a++) + if(strcmp(item[a].identifier, enumname) == 0) + return (item[a].value == RNA_property_enum_get(ptr, prop)); printf("RNA_enum_is_equal: %s.%s item %s not found.\n", ptr->type->identifier, name, enumname); return 0; @@ -2552,12 +2232,17 @@ char *RNA_pointer_as_string(PointerRNA *ptr) DynStr *dynstr= BLI_dynstr_new(); char *cstring; + PropertyRNA *prop, *iterprop; + CollectionPropertyIterator iter; const char *propname; int first_time = 1; BLI_dynstr_append(dynstr, "{"); - RNA_STRUCT_BEGIN(ptr, prop) { + iterprop= RNA_struct_iterator_property(ptr->type); + + for(RNA_property_collection_begin(ptr, iterprop, &iter); iter.valid; RNA_property_collection_next(&iter)) { + prop= iter.ptr.data; propname = RNA_property_identifier(prop); if(strcmp(propname, "rna_type")==0) @@ -2571,8 +2256,8 @@ char *RNA_pointer_as_string(PointerRNA *ptr) BLI_dynstr_appendf(dynstr, "\"%s\":%s", propname, cstring); MEM_freeN(cstring); } - RNA_STRUCT_END; + RNA_property_collection_end(&iter); BLI_dynstr_append(dynstr, "}"); @@ -2764,17 +2449,6 @@ ParameterList *RNA_parameter_list_create(PointerRNA *ptr, FunctionRNA *func) void RNA_parameter_list_free(ParameterList *parms) { - PropertyRNA *parm; - int tot; - - parm= parms->func->cont.properties.first; - for(tot= 0; parm; parm= parm->next) { - if(parm->type == PROP_COLLECTION) - BLI_freelistN((ListBase*)((char*)parms->data+tot)); - - tot+= rna_parameter_size(parm); - } - MEM_freeN(parms->data); parms->data= NULL; diff --git a/source/blender/makesrna/intern/rna_action.c b/source/blender/makesrna/intern/rna_action.c index 3639d6d3fff..588c94380dc 100644 --- a/source/blender/makesrna/intern/rna_action.c +++ b/source/blender/makesrna/intern/rna_action.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_action.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_actuator.c b/source/blender/makesrna/intern/rna_actuator.c index 3eb88e706e9..05d55d284a7 100644 --- a/source/blender/makesrna/intern/rna_actuator.c +++ b/source/blender/makesrna/intern/rna_actuator.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_actuator.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_animation.c b/source/blender/makesrna/intern/rna_animation.c index 2ed47effec1..d119783766d 100644 --- a/source/blender/makesrna/intern/rna_animation.c +++ b/source/blender/makesrna/intern/rna_animation.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_animation.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_armature.c b/source/blender/makesrna/intern/rna_armature.c index caa970eff57..389257e9331 100644 --- a/source/blender/makesrna/intern/rna_armature.c +++ b/source/blender/makesrna/intern/rna_armature.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_armature.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -443,30 +443,6 @@ void rna_EditBone_tail_selected_set(PointerRNA *ptr, int value) else data->flag &= ~BONE_TIPSEL; } -static void rna_Armature_bones_next(CollectionPropertyIterator *iter) -{ - ListBaseIterator *internal= iter->internal; - Bone *bone= (Bone*)internal->link; - - if(bone->childbase.first) - internal->link= (Link*)bone->childbase.first; - else if(bone->next) - internal->link= (Link*)bone->next; - else { - internal->link= NULL; - - do { - bone= bone->parent; - if(bone && bone->next) { - internal->link= (Link*)bone->next; - break; - } - } while(bone); - } - - iter->valid= (internal->link != NULL); -} - #else static void rna_def_bone_common(StructRNA *srna, int editbone) @@ -684,7 +660,6 @@ void rna_def_armature(BlenderRNA *brna) /* Collections */ prop= RNA_def_property(srna, "bones", PROP_COLLECTION, PROP_NONE); RNA_def_property_collection_sdna(prop, NULL, "bonebase", NULL); - RNA_def_property_collection_funcs(prop, 0, "rna_Armature_bones_next", 0, 0, 0, 0, 0, 0, 0); RNA_def_property_struct_type(prop, "Bone"); RNA_def_property_ui_text(prop, "Bones", ""); diff --git a/source/blender/makesrna/intern/rna_brush.c b/source/blender/makesrna/intern/rna_brush.c index 90617d01833..d3213c01846 100644 --- a/source/blender/makesrna/intern/rna_brush.c +++ b/source/blender/makesrna/intern/rna_brush.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_brush.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_camera.c b/source/blender/makesrna/intern/rna_camera.c index 4814f9583a9..928086b951c 100644 --- a/source/blender/makesrna/intern/rna_camera.c +++ b/source/blender/makesrna/intern/rna_camera.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_camera.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_cloth.c b/source/blender/makesrna/intern/rna_cloth.c index cefd2316fbf..7f61125bc11 100644 --- a/source/blender/makesrna/intern/rna_cloth.c +++ b/source/blender/makesrna/intern/rna_cloth.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_cloth.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -34,24 +34,9 @@ #include "BKE_modifier.h" #include "DNA_cloth_types.h" -#include "DNA_object_types.h" -#include "DNA_scene_types.h" - -#include "WM_types.h" #ifdef RNA_RUNTIME -#include "BKE_context.h" -#include "BKE_depsgraph.h" - -static void rna_cloth_update(bContext *C, PointerRNA *ptr) -{ - Scene *scene = CTX_data_scene(C); - Object *ob = ptr->id.data; - - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); -} - static void rna_ClothSettings_max_bend_set(struct PointerRNA *ptr, float value) { ClothSimSettings *settings = (ClothSimSettings*)ptr->data; @@ -180,50 +165,42 @@ static void rna_def_cloth_sim_settings(BlenderRNA *brna) RNA_def_property_float_sdna(prop, NULL, "mingoal"); RNA_def_property_range(prop, 0.0f, 1.0f); RNA_def_property_ui_text(prop, "Goal Minimum", "Goal minimum, vertex group weights are scaled to match this range."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "goal_max", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "maxgoal"); RNA_def_property_range(prop, 0.0f, 1.0f); RNA_def_property_ui_text(prop, "Goal Maximum", "Goal maximum, vertex group weights are scaled to match this range."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "goal_default", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "defgoal"); RNA_def_property_range(prop, 0.0f, 1.0f); RNA_def_property_ui_text(prop, "Goal Default", "Default Goal (vertex target position) value, when no Vertex Group used."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "goal_spring", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "goalspring"); RNA_def_property_range(prop, 0.0f, 0.999f); RNA_def_property_ui_text(prop, "Goal Stiffness", "Goal (vertex target position) spring stiffness."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "goal_friction", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "goalfrict"); RNA_def_property_range(prop, 0.0f, 50.0f); RNA_def_property_ui_text(prop, "Goal Damping", "Goal (vertex target position) friction."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); /* mass */ prop= RNA_def_property(srna, "mass", PROP_FLOAT, PROP_NONE); RNA_def_property_range(prop, 0.0f, 10.0f); RNA_def_property_ui_text(prop, "Mass", "Mass of cloth material."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "mass_vertex_group", PROP_STRING, PROP_NONE); RNA_def_property_string_funcs(prop, "rna_ClothSettings_mass_vgroup_get", "rna_ClothSettings_mass_vgroup_length", "rna_ClothSettings_mass_vgroup_set"); RNA_def_property_ui_text(prop, "Mass Vertex Group", "Vertex group for fine control over mass distribution."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "gravity", PROP_FLOAT, PROP_VECTOR); RNA_def_property_array(prop, 3); RNA_def_property_range(prop, -100.0, 100.0); RNA_def_property_float_funcs(prop, "rna_ClothSettings_gravity_get", "rna_ClothSettings_gravity_set", NULL); RNA_def_property_ui_text(prop, "Gravity", "Gravity or external force vector."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); /* various */ @@ -231,73 +208,61 @@ static void rna_def_cloth_sim_settings(BlenderRNA *brna) RNA_def_property_float_sdna(prop, NULL, "Cvi"); RNA_def_property_range(prop, 0.0f, 10.0f); RNA_def_property_ui_text(prop, "Air Damping", "Air has normally some thickness which slows falling things down."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "pin_cloth", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flags", CLOTH_SIMSETTINGS_FLAG_GOAL); RNA_def_property_ui_text(prop, "Pin Cloth", "Define forces for vertices to stick to animated position."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "pin_stiffness", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "goalspring"); RNA_def_property_range(prop, 0.0f, 50.0); RNA_def_property_ui_text(prop, "Pin Stiffness", "Pin (vertex target position) spring stiffness."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "quality", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "stepsPerFrame"); RNA_def_property_range(prop, 4, 80); RNA_def_property_ui_text(prop, "Quality", "Quality of the simulation in steps per frame (higher is better quality but slower)."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); /* springs */ prop= RNA_def_property(srna, "stiffness_scaling", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flags", CLOTH_SIMSETTINGS_FLAG_SCALING); RNA_def_property_ui_text(prop, "Stiffness Scaling", "If enabled, stiffness can be scaled along a weight painted vertex group."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "spring_damping", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "Cdis"); RNA_def_property_range(prop, 0.0f, 50.0f); RNA_def_property_ui_text(prop, "Spring Damping", "Damping of cloth velocity (higher = more smooth, less jiggling)"); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "structural_stiffness", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "structural"); RNA_def_property_range(prop, 1.0f, 10000.0f); RNA_def_property_ui_text(prop, "Structural Stiffness", "Overall stiffness of structure."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "structural_stiffness_max", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "max_struct"); RNA_def_property_range(prop, 0.0f, 10000.0f); RNA_def_property_float_funcs(prop, NULL, "rna_ClothSettings_max_struct_set", NULL); RNA_def_property_ui_text(prop, "Structural Stiffness Maximum", "Maximum structural stiffness value."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "structural_stiffness_vertex_group", PROP_STRING, PROP_NONE); RNA_def_property_string_funcs(prop, "rna_ClothSettings_struct_vgroup_get", "rna_ClothSettings_struct_vgroup_length", "rna_ClothSettings_struct_vgroup_set"); RNA_def_property_ui_text(prop, "Structural Stiffness Vertex Group", "Vertex group for fine control over structural stiffness."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "bending_stiffness", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "bending"); RNA_def_property_range(prop, 0.0f, 10000.0f); RNA_def_property_ui_text(prop, "Bending Stiffness", "Wrinkle coefficient (higher = less smaller but more big wrinkles)."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "bending_stiffness_max", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "max_bend"); RNA_def_property_range(prop, 0.0f, 10000.0f); RNA_def_property_float_funcs(prop, NULL, "rna_ClothSettings_max_bend_set", NULL); RNA_def_property_ui_text(prop, "Bending Stiffness Maximum", "Maximum bending stiffness value."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "bending_vertex_group", PROP_STRING, PROP_NONE); RNA_def_property_string_funcs(prop, "rna_ClothSettings_bend_vgroup_get", "rna_ClothSettings_bend_vgroup_length", "rna_ClothSettings_bend_vgroup_set"); RNA_def_property_ui_text(prop, "Bending Stiffness Vertex Group", "Vertex group for fine control over bending stiffness."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); /* unused */ @@ -358,48 +323,40 @@ static void rna_def_cloth_collision_settings(BlenderRNA *brna) prop= RNA_def_property(srna, "enable_collision", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flags", CLOTH_COLLSETTINGS_FLAG_ENABLED); RNA_def_property_ui_text(prop, "Enable Collision", "Enable collisions with other objects."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "min_distance", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "epsilon"); RNA_def_property_range(prop, 0.001f, 1.0f); RNA_def_property_ui_text(prop, "Minimum Distance", "Minimum distance between collision objects before collision response takes in, can be changed for each frame."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "friction", PROP_FLOAT, PROP_NONE); RNA_def_property_range(prop, 0.0f, 80.0f); RNA_def_property_ui_text(prop, "Friction", "Friction force if a collision happened (0=movement not changed, 100=no movement left)"); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "collision_quality", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "loop_count"); RNA_def_property_range(prop, 1, 20); RNA_def_property_ui_text(prop, "Collision Quality", "How many collision iterations should be done. (higher is better quality but slower)"); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); /* self collision */ prop= RNA_def_property(srna, "enable_self_collision", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flags", CLOTH_COLLSETTINGS_FLAG_SELF); RNA_def_property_ui_text(prop, "Enable Self Collision", "Enable self collisions."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "self_min_distance", PROP_FLOAT, PROP_NONE); RNA_def_property_float_sdna(prop, NULL, "selfepsilon"); RNA_def_property_range(prop, 0.5f, 1.0f); RNA_def_property_ui_text(prop, "Self Minimum Distance", "0.5 means no distance at all, 1.0 is maximum distance"); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "self_friction", PROP_FLOAT, PROP_NONE); RNA_def_property_range(prop, 0.0f, 80.0f); RNA_def_property_ui_text(prop, "Self Friction", "Friction/damping with self contact."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); prop= RNA_def_property(srna, "self_collision_quality", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "self_loop_count"); RNA_def_property_range(prop, 1, 10); RNA_def_property_ui_text(prop, "Self Collision Quality", "How many self collision iterations should be done. (higher is better quality but slower), can be changed for each frame."); - RNA_def_property_update(prop, NC_OBJECT|ND_GEOM_DATA, "rna_cloth_update"); } void RNA_def_cloth(BlenderRNA *brna) diff --git a/source/blender/makesrna/intern/rna_color.c b/source/blender/makesrna/intern/rna_color.c index 179808ab66d..c1464ec87f2 100644 --- a/source/blender/makesrna/intern/rna_color.c +++ b/source/blender/makesrna/intern/rna_color.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_color.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_constraint.c b/source/blender/makesrna/intern/rna_constraint.c index 8200a21f4ac..ec1676eea95 100644 --- a/source/blender/makesrna/intern/rna_constraint.c +++ b/source/blender/makesrna/intern/rna_constraint.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_constraint.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -534,14 +534,6 @@ static void rna_def_constraint_locate_like(BlenderRNA *brna) srna= RNA_def_struct(brna, "CopyLocationConstraint", "Constraint"); RNA_def_struct_ui_text(srna, "Copy Location Constraint", "Copies the location of the target."); - - RNA_def_struct_sdna(srna, "bConstraint"); - - prop= RNA_def_property(srna, "head_tail", PROP_FLOAT, PROP_PERCENTAGE); - RNA_def_property_float_sdna(prop, NULL, "headtail"); - RNA_def_property_ui_text(prop, "Head/Tail", "Target along length of bone: Head=0, Tail=1."); - RNA_def_property_update(prop, NC_OBJECT|ND_CONSTRAINT, "rna_Constraint_update"); - RNA_def_struct_sdna_from(srna, "bLocateLikeConstraint", "data"); prop= RNA_def_property(srna, "target", PROP_POINTER, PROP_NONE); @@ -590,6 +582,13 @@ static void rna_def_constraint_locate_like(BlenderRNA *brna) RNA_def_property_boolean_sdna(prop, NULL, "flag", LOCLIKE_OFFSET); RNA_def_property_ui_text(prop, "Offset", "Add original location into copied location."); RNA_def_property_update(prop, NC_OBJECT|ND_CONSTRAINT, "rna_Constraint_update"); + + RNA_def_struct_sdna(srna, "bConstraint"); + + prop= RNA_def_property(srna, "head_tail", PROP_FLOAT, PROP_PERCENTAGE); + RNA_def_property_float_sdna(prop, NULL, "headtail"); + RNA_def_property_ui_text(prop, "Head/Tail", "Target along length of bone: Head=0, Tail=1."); + RNA_def_property_update(prop, NC_OBJECT|ND_CONSTRAINT, "rna_Constraint_update"); } static void rna_def_constraint_minmax(BlenderRNA *brna) diff --git a/source/blender/makesrna/intern/rna_context.c b/source/blender/makesrna/intern/rna_context.c index 07a50235733..7624d4a1144 100644 --- a/source/blender/makesrna/intern/rna_context.c +++ b/source/blender/makesrna/intern/rna_context.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_context.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_controller.c b/source/blender/makesrna/intern/rna_controller.c index 4d5ef7aa123..47399090b4e 100644 --- a/source/blender/makesrna/intern/rna_controller.c +++ b/source/blender/makesrna/intern/rna_controller.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_controller.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_curve.c b/source/blender/makesrna/intern/rna_curve.c index 41a47e279e9..c592625c7dc 100644 --- a/source/blender/makesrna/intern/rna_curve.c +++ b/source/blender/makesrna/intern/rna_curve.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_curve.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_define.c b/source/blender/makesrna/intern/rna_define.c index 715f03bb3f1..98a2ae8b32d 100644 --- a/source/blender/makesrna/intern/rna_define.c +++ b/source/blender/makesrna/intern/rna_define.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_define.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -112,7 +112,7 @@ StructDefRNA *rna_find_struct_def(StructRNA *srna) return NULL; } -PropertyDefRNA *rna_find_struct_property_def(StructRNA *srna, PropertyRNA *prop) +PropertyDefRNA *rna_find_struct_property_def(PropertyRNA *prop) { StructDefRNA *dsrna; PropertyDefRNA *dprop; @@ -123,7 +123,7 @@ PropertyDefRNA *rna_find_struct_property_def(StructRNA *srna, PropertyRNA *prop) return NULL; } - dsrna= rna_find_struct_def(srna); + dsrna= rna_find_struct_def(DefRNA.laststruct); dprop= dsrna->cont.properties.last; for (; dprop; dprop= dprop->prev) if (dprop->prop==prop) @@ -150,7 +150,7 @@ PropertyDefRNA *rna_find_property_def(PropertyRNA *prop) return NULL; } - dprop= rna_find_struct_property_def(DefRNA.laststruct, prop); + dprop= rna_find_struct_property_def(prop); if (dprop) return dprop; @@ -1311,7 +1311,7 @@ static PropertyDefRNA *rna_def_property_sdna(PropertyRNA *prop, const char *stru StructDefRNA *ds; PropertyDefRNA *dp; - dp= rna_find_struct_property_def(DefRNA.laststruct, prop); + dp= rna_find_struct_property_def(prop); if (dp==NULL) return NULL; ds= rna_find_struct_def((StructRNA*)dp->cont); @@ -1371,7 +1371,7 @@ void RNA_def_property_boolean_negative_sdna(PropertyRNA *prop, const char *struc RNA_def_property_boolean_sdna(prop, structname, propname, booleanbit); - dp= rna_find_struct_property_def(DefRNA.laststruct, prop); + dp= rna_find_struct_property_def(prop); if(dp) dp->booleannegative= 1; @@ -1468,7 +1468,7 @@ void RNA_def_property_enum_bitflag_sdna(PropertyRNA *prop, const char *structnam RNA_def_property_enum_sdna(prop, structname, propname); - dp= rna_find_struct_property_def(DefRNA.laststruct, prop); + dp= rna_find_struct_property_def(prop); if(dp) dp->enumbitflags= 1; @@ -1946,7 +1946,7 @@ PropertyRNA *RNA_def_string_dir_path(StructOrFunctionRNA *cont_, const char *ide return prop; } -PropertyRNA *RNA_def_enum(StructOrFunctionRNA *cont_, const char *identifier, const EnumPropertyItem *items, int default_value, +PropertyRNA *RNA_def_enum(StructOrFunctionRNA *cont_, const char *identifier, EnumPropertyItem *items, int default_value, const char *ui_name, const char *ui_description) { ContainerRNA *cont= cont_; @@ -2249,6 +2249,7 @@ int rna_parameter_size(PropertyRNA *parm) #endif } case PROP_COLLECTION: + /* XXX does not work yet */ return sizeof(ListBase); } } diff --git a/source/blender/makesrna/intern/rna_fcurve.c b/source/blender/makesrna/intern/rna_fcurve.c index 806219ec6bf..70e511de323 100644 --- a/source/blender/makesrna/intern/rna_fcurve.c +++ b/source/blender/makesrna/intern/rna_fcurve.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_fcurve.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_fluidsim.c b/source/blender/makesrna/intern/rna_fluidsim.c index 4e047ff7772..ac51aa6d0d7 100644 --- a/source/blender/makesrna/intern/rna_fluidsim.c +++ b/source/blender/makesrna/intern/rna_fluidsim.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_fluidsim.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_group.c b/source/blender/makesrna/intern/rna_group.c index 1406ad1ae60..82bdd66802a 100644 --- a/source/blender/makesrna/intern/rna_group.c +++ b/source/blender/makesrna/intern/rna_group.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_group.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_image.c b/source/blender/makesrna/intern/rna_image.c index 4a6fdf5a734..7c8b0c3bf8e 100644 --- a/source/blender/makesrna/intern/rna_image.c +++ b/source/blender/makesrna/intern/rna_image.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_image.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -35,8 +35,6 @@ #include "BKE_context.h" #include "BKE_image.h" -#include "WM_types.h" - #ifdef RNA_RUNTIME static void rna_Image_animated_update(bContext *C, PointerRNA *ptr) @@ -135,19 +133,16 @@ static void rna_def_image(BlenderRNA *brna) RNA_def_property_string_sdna(prop, NULL, "name"); RNA_def_property_clear_flag(prop, PROP_EDITABLE); /* imagechanged */ RNA_def_property_ui_text(prop, "Filename", "Image/Movie file name."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "source", PROP_ENUM, PROP_NONE); RNA_def_property_enum_items(prop, prop_source_items); RNA_def_property_clear_flag(prop, PROP_EDITABLE); /* imagechanged */ RNA_def_property_ui_text(prop, "Source", "Where the image comes from."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "type", PROP_ENUM, PROP_NONE); RNA_def_property_enum_items(prop, prop_type_items); RNA_def_property_clear_flag(prop, PROP_EDITABLE); /* imagechanged */ RNA_def_property_ui_text(prop, "Type", "How to generate the image."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "packed_file", PROP_POINTER, PROP_NONE); RNA_def_property_pointer_sdna(prop, NULL, "packedfile"); @@ -157,105 +152,90 @@ static void rna_def_image(BlenderRNA *brna) prop= RNA_def_property(srna, "fields", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flag", IMA_FIELDS); RNA_def_property_ui_text(prop, "Fields", "Use fields of the image."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "odd_fields", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flag", IMA_STD_FIELD); RNA_def_property_ui_text(prop, "Odd Fields", "Standard field toggle."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "antialias", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flag", IMA_ANTIALI); RNA_def_property_ui_text(prop, "Anti-alias", "Toggles image anti-aliasing, only works with solid colors"); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "premultiply", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flag", IMA_DO_PREMUL); RNA_def_property_ui_text(prop, "Premultiply", "Convert RGB from key alpha to premultiplied alpha."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); /* generated image (image_generated_change_cb) */ prop= RNA_def_property(srna, "generated_type", PROP_ENUM, PROP_NONE); RNA_def_property_enum_sdna(prop, NULL, "gen_type"); RNA_def_property_enum_items(prop, prop_generated_type_items); RNA_def_property_ui_text(prop, "Generated Type", "Generated image type."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "generated_width", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "gen_x"); RNA_def_property_range(prop, 1, 16384); RNA_def_property_ui_text(prop, "Generated Width", "Generated image width."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "generated_height", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "gen_y"); RNA_def_property_range(prop, 1, 16384); RNA_def_property_ui_text(prop, "Generated Height", "Generated image height."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); /* realtime properties */ prop= RNA_def_property(srna, "mapping", PROP_ENUM, PROP_NONE); RNA_def_property_enum_bitflag_sdna(prop, NULL, "flag"); RNA_def_property_enum_items(prop, prop_mapping_items); RNA_def_property_ui_text(prop, "Mapping", "Mapping type to use for this image in the game engine."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "display_aspect", PROP_FLOAT, PROP_VECTOR); RNA_def_property_float_sdna(prop, NULL, "aspx"); RNA_def_property_array(prop, 2); RNA_def_property_range(prop, 0.1f, 5000.0f); RNA_def_property_ui_text(prop, "Display Aspect", "Display Aspect for this image, does not affect rendering."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "animated", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "tpageflag", IMA_TWINANIM); RNA_def_property_ui_text(prop, "Animated", "Use as animated texture in the game engine."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, "rna_Image_animated_update"); + RNA_def_property_update(prop, 0, "rna_Image_animated_update"); prop= RNA_def_property(srna, "animation_start", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "twsta"); RNA_def_property_range(prop, 0, 128); RNA_def_property_ui_text(prop, "Animation Start", "Start frame of an animated texture."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, "rna_Image_animated_update"); + RNA_def_property_update(prop, 0, "rna_Image_animated_update"); prop= RNA_def_property(srna, "animation_end", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "twend"); RNA_def_property_range(prop, 0, 128); RNA_def_property_ui_text(prop, "Animation End", "End frame of an animated texture."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, "rna_Image_animated_update"); + RNA_def_property_update(prop, 0, "rna_Image_animated_update"); prop= RNA_def_property(srna, "animation_speed", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "animspeed"); RNA_def_property_range(prop, 1, 100); RNA_def_property_ui_text(prop, "Animation Speed", "Speed of the animation in frames per second."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "tiles", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "tpageflag", IMA_TILES); RNA_def_property_ui_text(prop, "Tiles", "Use of tilemode for faces (default shift-LMB to pick the tile for selected faces)."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "tiles_x", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "xrep"); RNA_def_property_range(prop, 1, 16); RNA_def_property_ui_text(prop, "Tiles X", "Degree of repetition in the X direction."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "tiles_y", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "yrep"); RNA_def_property_range(prop, 1, 16); RNA_def_property_ui_text(prop, "Tiles Y", "Degree of repetition in the Y direction."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "clamp_x", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "tpageflag", IMA_CLAMP_U); RNA_def_property_ui_text(prop, "Clamp X", "Disable texture repeating horizontally."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); prop= RNA_def_property(srna, "clamp_y", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "tpageflag", IMA_CLAMP_V); RNA_def_property_ui_text(prop, "Clamp Y", "Disable texture repeating vertically."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); } void RNA_def_image(BlenderRNA *brna) diff --git a/source/blender/makesrna/intern/rna_internal.h b/source/blender/makesrna/intern/rna_internal.h index 3d66682771d..a41f522bb0f 100644 --- a/source/blender/makesrna/intern/rna_internal.h +++ b/source/blender/makesrna/intern/rna_internal.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_internal.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -145,6 +145,7 @@ void RNA_def_object_force(struct BlenderRNA *brna); void RNA_def_packedfile(struct BlenderRNA *brna); void RNA_def_particle(struct BlenderRNA *brna); void RNA_def_pose(struct BlenderRNA *brna); +void RNA_def_radio(struct BlenderRNA *brna); void RNA_def_rna(struct BlenderRNA *brna); void RNA_def_scene(struct BlenderRNA *brna); void RNA_def_screen(struct BlenderRNA *brna); @@ -255,7 +256,6 @@ void rna_freelistN(struct ListBase *listbase); StructDefRNA *rna_find_struct_def(StructRNA *srna); FunctionDefRNA *rna_find_function_def(FunctionRNA *func); PropertyDefRNA *rna_find_parameter_def(PropertyRNA *parm); -PropertyDefRNA *rna_find_struct_property_def(StructRNA *srna, PropertyRNA *prop); /* Pointer Handling */ diff --git a/source/blender/makesrna/intern/rna_internal_types.h b/source/blender/makesrna/intern/rna_internal_types.h index 401b430ebc9..3cf250151c7 100644 --- a/source/blender/makesrna/intern/rna_internal_types.h +++ b/source/blender/makesrna/intern/rna_internal_types.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_internal_types.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -146,10 +146,6 @@ struct PropertyRNA { /* callback for testing if editable/evaluated */ EditableFunc editable; - - /* raw access */ - int rawoffset; - RawPropertyType rawtype; }; /* Property Types */ diff --git a/source/blender/makesrna/intern/rna_key.c b/source/blender/makesrna/intern/rna_key.c index 71e424bbd69..b97dd95c4d4 100644 --- a/source/blender/makesrna/intern/rna_key.c +++ b/source/blender/makesrna/intern/rna_key.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_key.c 19382 2009-03-23 13:24:48Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_lamp.c b/source/blender/makesrna/intern/rna_lamp.c index a49b4377d9d..c6cf2b0a410 100644 --- a/source/blender/makesrna/intern/rna_lamp.c +++ b/source/blender/makesrna/intern/rna_lamp.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_lamp.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -253,11 +253,11 @@ static void rna_def_lamp(BlenderRNA *brna) PropertyRNA *prop; static EnumPropertyItem prop_type_items[] = { - {LA_LOCAL, "POINT", ICON_LAMP_POINT, "Point", "Omnidirectional point light source."}, - {LA_SUN, "SUN", ICON_LAMP_SUN, "Sun", "Constant direction parallel ray light source."}, - {LA_SPOT, "SPOT", ICON_LAMP_SPOT, "Spot", "Directional cone light source."}, - {LA_HEMI, "HEMI", ICON_LAMP_HEMI, "Hemi", "180 degree constant light source."}, - {LA_AREA, "AREA", ICON_LAMP_AREA, "Area", "Directional area light source."}, + {LA_LOCAL, "POINT", 0, "Point", "Omnidirectional point light source."}, + {LA_SUN, "SUN", 0, "Sun", "Constant direction parallel ray light source."}, + {LA_SPOT, "SPOT", 0, "Spot", "Directional cone light source."}, + {LA_HEMI, "HEMI", 0, "Hemi", "180 degree constant light source."}, + {LA_AREA, "AREA", 0, "Area", "Directional area light source."}, {0, NULL, 0, NULL, NULL}}; srna= RNA_def_struct(brna, "Lamp", "ID"); diff --git a/source/blender/makesrna/intern/rna_lattice.c b/source/blender/makesrna/intern/rna_lattice.c index f67267ce0d0..3af448b0233 100644 --- a/source/blender/makesrna/intern/rna_lattice.c +++ b/source/blender/makesrna/intern/rna_lattice.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_lattice.c 19382 2009-03-23 13:24:48Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_main.c b/source/blender/makesrna/intern/rna_main.c index 26fc3c2941e..6b1ce8c02ae 100644 --- a/source/blender/makesrna/intern/rna_main.c +++ b/source/blender/makesrna/intern/rna_main.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_main.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -264,7 +264,7 @@ void RNA_def_main(BlenderRNA *brna) { prop= RNA_def_property(srna, lists[i][0], PROP_COLLECTION, PROP_NONE); RNA_def_property_struct_type(prop, lists[i][1]); - RNA_def_property_collection_funcs(prop, lists[i][2], "rna_iterator_listbase_next", "rna_iterator_listbase_end", "rna_iterator_listbase_get", 0, 0, 0, 0, 0); + RNA_def_property_collection_funcs(prop, lists[i][2], "rna_iterator_listbase_next", "rna_iterator_listbase_end", "rna_iterator_listbase_get", 0, 0, 0, "add_mesh", "remove_mesh"); RNA_def_property_ui_text(prop, lists[i][3], lists[i][4]); } diff --git a/source/blender/makesrna/intern/rna_main_api.c b/source/blender/makesrna/intern/rna_main_api.c index 6d56b2b00f9..2d699b6b229 100644 --- a/source/blender/makesrna/intern/rna_main_api.c +++ b/source/blender/makesrna/intern/rna_main_api.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_main_api.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_material.c b/source/blender/makesrna/intern/rna_material.c index 41f31594f6e..66e30f7ee50 100644 --- a/source/blender/makesrna/intern/rna_material.c +++ b/source/blender/makesrna/intern/rna_material.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_material.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_mesh.c b/source/blender/makesrna/intern/rna_mesh.c index e56760f5ca3..25b8739e074 100644 --- a/source/blender/makesrna/intern/rna_mesh.c +++ b/source/blender/makesrna/intern/rna_mesh.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_mesh.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -234,29 +234,6 @@ static int rna_Mesh_uv_layers_length(PointerRNA *ptr) return rna_CustomDataLayer_length(ptr, CD_MTFACE); } -static PointerRNA rna_Mesh_active_uv_layer_get(PointerRNA *ptr) -{ - Mesh *me= (Mesh*)ptr->data; - int index= CustomData_get_active_layer_index(&me->fdata, CD_MTFACE); - CustomDataLayer *cdl= (index == -1)? NULL: &me->fdata.layers[index]; - - return rna_pointer_inherit_refine(ptr, &RNA_MeshTextureFaceLayer, cdl); -} - -static void rna_Mesh_active_uv_layer_set(PointerRNA *ptr, PointerRNA value) -{ - Mesh *me= (Mesh*)ptr->data; - CustomDataLayer *cdl; - int a; - - for(cdl=me->fdata.layers, a=0; a<me->fdata.totlayer; cdl++, a++) { - if(value.data == cdl) { - CustomData_set_layer_active_index(&me->fdata, CD_MTFACE, a); - return; - } - } -} - static void rna_MeshTextureFace_uv1_get(PointerRNA *ptr, float *values) { MTFace *mtface= (MTFace*)ptr->data; @@ -371,29 +348,6 @@ static int rna_Mesh_vcol_layers_length(PointerRNA *ptr) return rna_CustomDataLayer_length(ptr, CD_MCOL); } -static PointerRNA rna_Mesh_active_vcol_layer_get(PointerRNA *ptr) -{ - Mesh *me= (Mesh*)ptr->data; - int index= CustomData_get_active_layer_index(&me->fdata, CD_MCOL); - CustomDataLayer *cdl= (index == -1)? NULL: &me->fdata.layers[index]; - - return rna_pointer_inherit_refine(ptr, &RNA_MeshColorLayer, cdl); -} - -static void rna_Mesh_active_vcol_layer_set(PointerRNA *ptr, PointerRNA value) -{ - Mesh *me= (Mesh*)ptr->data; - CustomDataLayer *cdl; - int a; - - for(cdl=me->fdata.layers, a=0; a<me->fdata.totlayer; cdl++, a++) { - if(value.data == cdl) { - CustomData_set_layer_active_index(&me->fdata, CD_MCOL, a); - return; - } - } -} - static void rna_MeshColorLayer_data_begin(CollectionPropertyIterator *iter, PointerRNA *ptr) { Mesh *me= (Mesh*)ptr->id.data; @@ -1121,34 +1075,18 @@ static void rna_def_mesh(BlenderRNA *brna) RNA_def_property_struct_type(prop, "MeshSticky"); RNA_def_property_ui_text(prop, "Sticky", "Sticky texture coordinates."); - /* UV layers */ - prop= RNA_def_property(srna, "uv_layers", PROP_COLLECTION, PROP_NONE); RNA_def_property_collection_sdna(prop, NULL, "fdata.layers", "fdata.totlayer"); RNA_def_property_collection_funcs(prop, "rna_Mesh_uv_layers_begin", 0, 0, 0, "rna_Mesh_uv_layers_length", 0, 0, 0, 0); RNA_def_property_struct_type(prop, "MeshTextureFaceLayer"); RNA_def_property_ui_text(prop, "UV Layers", ""); - prop= RNA_def_property(srna, "active_uv_layer", PROP_POINTER, PROP_UNSIGNED); - RNA_def_property_struct_type(prop, "MeshTextureFaceLayer"); - RNA_def_property_pointer_funcs(prop, "rna_Mesh_active_uv_layer_get", "rna_Mesh_active_uv_layer_set", NULL); - RNA_def_property_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Active UV Layer", "Active UV layer."); - - /* VCol layers */ - prop= RNA_def_property(srna, "vcol_layers", PROP_COLLECTION, PROP_NONE); RNA_def_property_collection_sdna(prop, NULL, "fdata.layers", "fdata.totlayer"); RNA_def_property_collection_funcs(prop, "rna_Mesh_vcol_layers_begin", 0, 0, 0, "rna_Mesh_vcol_layers_length", 0, 0, 0, 0); RNA_def_property_struct_type(prop, "MeshColorLayer"); RNA_def_property_ui_text(prop, "Vertex Color Layers", ""); - prop= RNA_def_property(srna, "active_vcol_layer", PROP_POINTER, PROP_UNSIGNED); - RNA_def_property_struct_type(prop, "MeshColorLayer"); - RNA_def_property_pointer_funcs(prop, "rna_Mesh_active_vcol_layer_get", "rna_Mesh_active_vcol_layer_set", NULL); - RNA_def_property_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Active Vertex Color Layer", "Active vertex color layer."); - prop= RNA_def_property(srna, "float_layers", PROP_COLLECTION, PROP_NONE); RNA_def_property_collection_sdna(prop, NULL, "fdata.layers", "fdata.totlayer"); RNA_def_property_collection_funcs(prop, "rna_Mesh_float_layers_begin", 0, 0, 0, "rna_Mesh_float_layers_length", 0, 0, 0, 0); diff --git a/source/blender/makesrna/intern/rna_mesh_api.c b/source/blender/makesrna/intern/rna_mesh_api.c index 26fb77777d7..02c079920ea 100644 --- a/source/blender/makesrna/intern/rna_mesh_api.c +++ b/source/blender/makesrna/intern/rna_mesh_api.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_mesh_api.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_meta.c b/source/blender/makesrna/intern/rna_meta.c index 5f95336af2d..ce5b883f0a9 100644 --- a/source/blender/makesrna/intern/rna_meta.c +++ b/source/blender/makesrna/intern/rna_meta.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_meta.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_modifier.c b/source/blender/makesrna/intern/rna_modifier.c index 9b3ff6e74a0..4c7bb3f52da 100644 --- a/source/blender/makesrna/intern/rna_modifier.c +++ b/source/blender/makesrna/intern/rna_modifier.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_modifier.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -41,35 +41,35 @@ #include "WM_types.h" EnumPropertyItem modifier_type_items[] ={ - {eModifierType_Armature, "ARMATURE", ICON_MOD_ARMATURE, "Armature", ""}, - {eModifierType_Array, "ARRAY", ICON_MOD_ARRAY, "Array", ""}, - {eModifierType_Bevel, "BEVEL", ICON_MOD_BEVEL, "Bevel", ""}, - {eModifierType_Boolean, "BOOLEAN", ICON_MOD_BOOLEAN, "Boolean", ""}, - {eModifierType_Build, "BUILD", ICON_MOD_BUILD, "Build", ""}, - {eModifierType_Cast, "CAST", ICON_MOD_CAST, "Cast", ""}, - {eModifierType_Cloth, "CLOTH", ICON_MOD_CLOTH, "Cloth", ""}, - {eModifierType_Collision, "COLLISION", ICON_MOD_PHYSICS, "Collision", ""}, - {eModifierType_Curve, "CURVE", ICON_MOD_CURVE, "Curve", ""}, - {eModifierType_Decimate, "DECIMATE", ICON_MOD_DECIM, "Decimate", ""}, - {eModifierType_Displace, "DISPLACE", ICON_MOD_DISPLACE, "Displace", ""}, - {eModifierType_EdgeSplit, "EDGE_SPLIT", ICON_MOD_EDGESPLIT, "Edge Split", ""}, - {eModifierType_Explode, "EXPLODE", ICON_MOD_EXPLODE, "Explode", ""}, - {eModifierType_Fluidsim, "FLUID_SIMULATION", ICON_MOD_FLUIDSIM, "Fluid Simulation", ""}, - {eModifierType_Hook, "HOOK", ICON_HOOK, "Hook", ""}, - {eModifierType_Lattice, "LATTICE", ICON_MOD_LATTICE, "Lattice", ""}, - {eModifierType_Mask, "MASK", ICON_MOD_MASK, "Mask", ""}, - {eModifierType_MeshDeform, "MESH_DEFORM", ICON_MOD_MESHDEFORM, "Mesh Deform", ""}, - {eModifierType_Mirror, "MIRROR", ICON_MOD_MIRROR, "Mirror", ""}, - {eModifierType_Multires, "MULTIRES", ICON_MOD_MULTIRES, "Multires", ""}, - {eModifierType_ParticleInstance, "PARTICLE_INSTANCE", ICON_MOD_PARTICLES, "Particle Instance", ""}, - {eModifierType_ParticleSystem, "PARTICLE_SYSTEM", ICON_MOD_PARTICLES, "Particle System", ""}, - {eModifierType_Shrinkwrap, "SHRINKWRAP", ICON_MOD_SHRINKWRAP, "Shrinkwrap", ""}, - {eModifierType_SimpleDeform, "SIMPLE_DEFORM", ICON_MOD_SIMPLEDEFORM, "Simple Deform", ""}, - {eModifierType_Smooth, "SMOOTH", ICON_MOD_SMOOTH, "Smooth", ""}, - {eModifierType_Softbody, "SOFTBODY", ICON_MOD_SOFT, "Softbody", ""}, - {eModifierType_Subsurf, "SUBSURF", ICON_MOD_SUBSURF, "Subsurf", ""}, - {eModifierType_UVProject, "UV_PROJECT", ICON_MOD_UVPROJECT, "UV Project", ""}, - {eModifierType_Wave, "WAVE", ICON_MOD_WAVE, "Wave", ""}, + {eModifierType_Armature, "ARMATURE", 0, "Armature", ""}, + {eModifierType_Array, "ARRAY", 0, "Array", ""}, + {eModifierType_Bevel, "BEVEL", 0, "Bevel", ""}, + {eModifierType_Boolean, "BOOLEAN", 0, "Boolean", ""}, + {eModifierType_Build, "BUILD", 0, "Build", ""}, + {eModifierType_Cast, "CAST", 0, "Cast", ""}, + {eModifierType_Cloth, "CLOTH", 0, "Cloth", ""}, + {eModifierType_Collision, "COLLISION", 0, "Collision", ""}, + {eModifierType_Curve, "CURVE", 0, "Curve", ""}, + {eModifierType_Decimate, "DECIMATE", 0, "Decimate", ""}, + {eModifierType_Displace, "DISPLACE", 0, "Displace", ""}, + {eModifierType_EdgeSplit, "EDGE_SPLIT", 0, "Edge Split", ""}, + {eModifierType_Explode, "EXPLODE", 0, "Explode", ""}, + {eModifierType_Fluidsim, "FLUID_SIMULATION", 0, "Fluid Simulation", ""}, + {eModifierType_Hook, "HOOK", 0, "Hook", ""}, + {eModifierType_Lattice, "LATTICE", 0, "Lattice", ""}, + {eModifierType_Mask, "MASK", 0, "Mask", ""}, + {eModifierType_MeshDeform, "MESH_DEFORM", 0, "Mesh Deform", ""}, + {eModifierType_Mirror, "MIRROR", 0, "Mirror", ""}, + {eModifierType_Multires, "MULTIRES", 0, "Multires", ""}, + {eModifierType_ParticleInstance, "PARTICLE_INSTANCE", 0, "Particle Instance", ""}, + {eModifierType_ParticleSystem, "PARTICLE_SYSTEM", 0, "Particle System", ""}, + {eModifierType_Shrinkwrap, "SHRINKWRAP", 0, "Shrinkwrap", ""}, + {eModifierType_SimpleDeform, "SIMPLE_DEFORM", 0, "Simple Deform", ""}, + {eModifierType_Smooth, "SMOOTH", 0, "Smooth", ""}, + {eModifierType_Softbody, "SOFTBODY", 0, "Softbody", ""}, + {eModifierType_Subsurf, "SUBSURF", 0, "Subsurf", ""}, + {eModifierType_UVProject, "UV_PROJECT", 0, "UV Project", ""}, + {eModifierType_Wave, "WAVE", 0, "Wave", ""}, {0, NULL, 0, NULL, NULL}}; diff --git a/source/blender/makesrna/intern/rna_nodetree.c b/source/blender/makesrna/intern/rna_nodetree.c index b35b02b2063..bad3d36bfc2 100644 --- a/source/blender/makesrna/intern/rna_nodetree.c +++ b/source/blender/makesrna/intern/rna_nodetree.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_nodetree.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_nodetree_types.h b/source/blender/makesrna/intern/rna_nodetree_types.h index 47a7be163b1..cff3984a56a 100644 --- a/source/blender/makesrna/intern/rna_nodetree_types.h +++ b/source/blender/makesrna/intern/rna_nodetree_types.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_nodetree_types.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_object.c b/source/blender/makesrna/intern/rna_object.c index 9b3100c733b..8fa07ecf813 100644 --- a/source/blender/makesrna/intern/rna_object.c +++ b/source/blender/makesrna/intern/rna_object.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_object.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -33,7 +33,6 @@ #include "DNA_customdata_types.h" #include "DNA_material_types.h" #include "DNA_mesh_types.h" -#include "DNA_object_force.h" #include "DNA_object_types.h" #include "DNA_property_types.h" #include "DNA_scene_types.h" @@ -241,25 +240,6 @@ static PointerRNA rna_Object_active_material_get(PointerRNA *ptr) return rna_pointer_inherit_refine(ptr, &RNA_MaterialSlot, ob->mat+ob->actcol); } -static void rna_Object_active_particle_system_index_range(PointerRNA *ptr, int *min, int *max) -{ - Object *ob= (Object*)ptr->id.data; - *min= 1; - *max= BLI_countlist(&ob->particlesystem); -} - -static int rna_Object_active_particle_system_index_get(PointerRNA *ptr) -{ - Object *ob= (Object*)ptr->id.data; - return psys_get_current_num(ob) + 1; -} - -static void rna_Object_active_particle_system_index_set(struct PointerRNA *ptr, int value) -{ - Object *ob= (Object*)ptr->id.data; - psys_set_current_num(ob, value); -} - #if 0 static void rna_Object_active_material_set(PointerRNA *ptr, PointerRNA value) { @@ -429,13 +409,11 @@ static void rna_def_material_slot(BlenderRNA *brna) RNA_def_property_flag(prop, PROP_EDITABLE); RNA_def_property_pointer_funcs(prop, "rna_MaterialSlot_material_get", "rna_MaterialSlot_material_set", NULL); RNA_def_property_ui_text(prop, "Material", "Material datablock used by this material slot."); - RNA_def_property_update(prop, NC_OBJECT|ND_SHADING, "rna_Object_update"); prop= RNA_def_property(srna, "link", PROP_ENUM, PROP_NONE); RNA_def_property_enum_items(prop, link_items); RNA_def_property_enum_funcs(prop, "rna_MaterialSlot_link_get", "rna_MaterialSlot_link_set", NULL); RNA_def_property_ui_text(prop, "Link", "Link material to object or the object's data."); - RNA_def_property_update(prop, NC_OBJECT|ND_SHADING, "rna_Object_update"); prop= RNA_def_property(srna, "name", PROP_STRING, PROP_NONE); RNA_def_property_string_funcs(prop, "rna_MaterialSlot_name_get", "rna_MaterialSlot_name_length", NULL); @@ -948,10 +926,6 @@ static void rna_def_object(BlenderRNA *brna) RNA_def_property_pointer_funcs(prop, "rna_Object_active_particle_system_get", NULL, NULL); RNA_def_property_ui_text(prop, "Active Particle System", "Active particle system being displayed"); - prop= RNA_def_property(srna, "active_particle_system_index", PROP_INT, PROP_UNSIGNED); - RNA_def_property_int_funcs(prop, "rna_Object_active_particle_system_index_get", "rna_Object_active_particle_system_index_set", "rna_Object_active_particle_system_index_range"); - RNA_def_property_ui_text(prop, "Active Particle System Index", "Index of active particle system slot."); - /* restrict */ prop= RNA_def_property(srna, "restrict_view", PROP_BOOLEAN, PROP_NONE); diff --git a/source/blender/makesrna/intern/rna_object_api.c b/source/blender/makesrna/intern/rna_object_api.c index 053ab115b3b..4ed97164988 100644 --- a/source/blender/makesrna/intern/rna_object_api.c +++ b/source/blender/makesrna/intern/rna_object_api.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_object_api.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_object_force.c b/source/blender/makesrna/intern/rna_object_force.c index 4d8c728db12..41ff8c98f73 100644 --- a/source/blender/makesrna/intern/rna_object_force.c +++ b/source/blender/makesrna/intern/rna_object_force.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_object_force.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -31,225 +31,9 @@ #include "DNA_object_types.h" #include "DNA_object_force.h" -#include "DNA_scene_types.h" - -#include "WM_types.h" #ifdef RNA_RUNTIME -#include "MEM_guardedalloc.h" - -#include "BKE_context.h" -#include "BKE_pointcache.h" -#include "BKE_depsgraph.h" - -#include "BLI_blenlib.h" - -static void rna_Cache_change(bContext *C, PointerRNA *ptr) -{ - Scene *scene = CTX_data_scene(C); - Object *ob = CTX_data_active_object(C); - PointCache *cache = (PointCache*)ptr->data; - PTCacheID *pid = NULL; - ListBase pidlist; - - if(!ob) - return; - - cache->flag |= PTCACHE_OUTDATED; - - BKE_ptcache_ids_from_object(&pidlist, ob); - - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); - - for(pid=pidlist.first; pid; pid=pid->next) { - if(pid->cache==cache) - break; - } - - if(pid) - BKE_ptcache_update_info(pid); - - BLI_freelistN(&pidlist); -} - -static void rna_Cache_toggle_disk_cache(bContext *C, PointerRNA *ptr) -{ - Object *ob = CTX_data_active_object(C); - PointCache *cache = (PointCache*)ptr->data; - PTCacheID *pid = NULL; - ListBase pidlist; - - if(!ob) - return; - - BKE_ptcache_ids_from_object(&pidlist, ob); - - for(pid=pidlist.first; pid; pid=pid->next) { - if(pid->cache==cache) - break; - } - - if(pid) - BKE_ptcache_toggle_disk_cache(pid); - - BLI_freelistN(&pidlist); -} - -static void rna_Cache_idname_change(bContext *C, PointerRNA *ptr) -{ - Object *ob = CTX_data_active_object(C); - PointCache *cache = (PointCache*)ptr->data; - PTCacheID *pid = NULL, *pid2; - ListBase pidlist; - int new_name = 1; - char name[80]; - - if(!ob) - return; - - /* TODO: check for proper characters */ - - BKE_ptcache_ids_from_object(&pidlist, ob); - - for(pid=pidlist.first; pid; pid=pid->next) { - if(pid->cache==cache) - pid2 = pid; - else if(strcmp(cache->name, "") && strcmp(cache->name,pid->cache->name)==0) { - /*TODO: report "name exists" to user */ - strcpy(cache->name, cache->prev_name); - new_name = 0; - } - } - - if(new_name) { - if(pid2 && cache->flag & PTCACHE_DISK_CACHE) { - strcpy(name, cache->name); - strcpy(cache->name, cache->prev_name); - - cache->flag &= ~PTCACHE_DISK_CACHE; - - BKE_ptcache_toggle_disk_cache(pid2); - - strcpy(cache->name, name); - - cache->flag |= PTCACHE_DISK_CACHE; - - BKE_ptcache_toggle_disk_cache(pid2); - } - - strcpy(cache->prev_name, cache->name); - } - - BLI_freelistN(&pidlist); -} - -static int rna_SoftBodySettings_use_edges_get(PointerRNA *ptr) -{ - Object *data= (Object*)(ptr->data); - return (((data->softflag) & OB_SB_EDGES) != 0); -} - -static void rna_SoftBodySettings_use_edges_set(PointerRNA *ptr, int value) -{ - Object *data= (Object*)(ptr->data); - if(value) data->softflag |= OB_SB_EDGES; - else data->softflag &= ~OB_SB_EDGES; -} - -static int rna_SoftBodySettings_use_goal_get(PointerRNA *ptr) -{ - Object *data= (Object*)(ptr->data); - return (((data->softflag) & OB_SB_GOAL) != 0); -} - -static void rna_SoftBodySettings_use_goal_set(PointerRNA *ptr, int value) -{ - Object *data= (Object*)(ptr->data); - if(value) data->softflag |= OB_SB_GOAL; - else data->softflag &= ~OB_SB_GOAL; -} - -static int rna_SoftBodySettings_stiff_quads_get(PointerRNA *ptr) -{ - Object *data= (Object*)(ptr->data); - return (((data->softflag) & OB_SB_QUADS) != 0); -} - -static void rna_SoftBodySettings_stiff_quads_set(PointerRNA *ptr, int value) -{ - Object *data= (Object*)(ptr->data); - if(value) data->softflag |= OB_SB_QUADS; - else data->softflag &= ~OB_SB_QUADS; -} - -static int rna_SoftBodySettings_self_collision_get(PointerRNA *ptr) -{ - Object *data= (Object*)(ptr->data); - return (((data->softflag) & OB_SB_SELF) != 0); -} - -static void rna_SoftBodySettings_self_collision_set(PointerRNA *ptr, int value) -{ - Object *data= (Object*)(ptr->data); - if(value) data->softflag |= OB_SB_SELF; - else data->softflag &= ~OB_SB_SELF; -} - -static int rna_SoftBodySettings_new_aero_get(PointerRNA *ptr) -{ - Object *data= (Object*)(ptr->data); - return (((data->softflag) & OB_SB_AERO_ANGLE) != 0); -} - -static void rna_SoftBodySettings_new_aero_set(PointerRNA *ptr, int value) -{ - Object *data= (Object*)(ptr->data); - if(value) data->softflag |= OB_SB_AERO_ANGLE; - else data->softflag &= ~OB_SB_AERO_ANGLE; -} - -static int rna_SoftBodySettings_enabled_get(PointerRNA *ptr) -{ - Object *data= (Object*)(ptr->data); - return (((data->softflag) & OB_SB_ENABLE) != 0); -} - -#if 0 -static void rna_SoftBodySettings_enabled_set(PointerRNA *ptr, int value) -{ - Object *data= (Object*)(ptr->data); - if(value) data->softflag |= OB_SB_ENABLE; - else data->softflag &= ~OB_SB_ENABLE; -} -#endif - -static int rna_SoftBodySettings_face_collision_get(PointerRNA *ptr) -{ - Object *data= (Object*)(ptr->data); - return (((data->softflag) & OB_SB_FACECOLL) != 0); -} - -static void rna_SoftBodySettings_face_collision_set(PointerRNA *ptr, int value) -{ - Object *data= (Object*)(ptr->data); - if(value) data->softflag |= OB_SB_FACECOLL; - else data->softflag &= ~OB_SB_FACECOLL; -} - -static int rna_SoftBodySettings_edge_collision_get(PointerRNA *ptr) -{ - Object *data= (Object*)(ptr->data); - return (((data->softflag) & OB_SB_EDGECOLL) != 0); -} - -static void rna_SoftBodySettings_edge_collision_set(PointerRNA *ptr, int value) -{ - Object *data= (Object*)(ptr->data); - if(value) data->softflag |= OB_SB_EDGECOLL; - else data->softflag &= ~OB_SB_EDGECOLL; -} - #else static void rna_def_pointcache(BlenderRNA *brna) @@ -270,47 +54,12 @@ static void rna_def_pointcache(BlenderRNA *brna) RNA_def_property_range(prop, 1, 300000); RNA_def_property_ui_text(prop, "End", "Frame on which the simulation stops."); - prop= RNA_def_property(srna, "step", PROP_INT, PROP_NONE); - RNA_def_property_int_sdna(prop, NULL, "step"); - RNA_def_property_range(prop, 1, 20); - RNA_def_property_ui_text(prop, "Cache Step", "Number of frames between cached frames."); - RNA_def_property_update(prop, NC_OBJECT, "rna_Cache_change"); - /* flags */ prop= RNA_def_property(srna, "baked", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flag", PTCACHE_BAKED); prop= RNA_def_property(srna, "baking", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flag", PTCACHE_BAKING); - - prop= RNA_def_property(srna, "disk_cache", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "flag", PTCACHE_DISK_CACHE); - RNA_def_property_ui_text(prop, "Disk Cache", "Save cache files to disk"); - RNA_def_property_update(prop, NC_OBJECT, "rna_Cache_toggle_disk_cache"); - - prop= RNA_def_property(srna, "outdated", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "flag", PTCACHE_OUTDATED); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Cache is outdated", ""); - - prop= RNA_def_property(srna, "frames_skipped", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "flag", PTCACHE_FRAMES_SKIPPED); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - - prop= RNA_def_property(srna, "name", PROP_STRING, PROP_NONE); - RNA_def_property_string_sdna(prop, NULL, "name"); - RNA_def_property_ui_text(prop, "Name", "Cache name"); - RNA_def_property_update(prop, NC_OBJECT, "rna_Cache_idname_change"); - - prop= RNA_def_property(srna, "quick_cache", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "flag", PTCACHE_QUICK_CACHE); - RNA_def_property_ui_text(prop, "Quick Cache", "Update simulation with cache steps"); - RNA_def_property_update(prop, NC_OBJECT, "rna_Cache_change"); - - prop= RNA_def_property(srna, "info", PROP_STRING, PROP_NONE); - RNA_def_property_string_sdna(prop, NULL, "info"); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Cache Info", "Info on current cache status."); } static void rna_def_collision(BlenderRNA *brna) @@ -414,7 +163,6 @@ static void rna_def_field(BlenderRNA *brna) srna= RNA_def_struct(brna, "FieldSettings", NULL); RNA_def_struct_sdna(srna, "PartDeflect"); RNA_def_struct_ui_text(srna, "Field Settings", "Field settings for an object in physics simulation."); - RNA_def_struct_ui_icon(srna, ICON_PHYSICS); /* Enums */ @@ -557,206 +305,10 @@ static void rna_def_game_softbody(BlenderRNA *brna) static void rna_def_softbody(BlenderRNA *brna) { StructRNA *srna; - PropertyRNA *prop; - - static EnumPropertyItem collision_type_items[] = { - {SBC_MODE_MANUAL, "MANUAL", 0, "Manual", "Manual adjust"}, - {SBC_MODE_AVG, "AVERAGE", 0, "Average", "Average Spring lenght * Ball Size"}, - {SBC_MODE_MIN, "MINIMAL", 0, "Minimal", "Minimal Spring lenght * Ball Size"}, - {SBC_MODE_MAX, "MAXIMAL", 0, "Maximal", "Maximal Spring lenght * Ball Size"}, - {SBC_MODE_AVGMINMAX, "MINMAX", 0, "AvMinMax", "(Min+Max)/2 * Ball Size"}, - {0, NULL, 0, NULL, NULL}}; srna= RNA_def_struct(brna, "SoftBodySettings", NULL); RNA_def_struct_sdna(srna, "SoftBody"); RNA_def_struct_ui_text(srna, "Soft Body Settings", "Soft body simulation settings for an object."); - - /* General Settings */ - - prop= RNA_def_property(srna, "friction", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "mediafrict"); - RNA_def_property_range(prop, 0.0f, 50.0f); - RNA_def_property_ui_text(prop, "Friction", "General media friction for point movements"); - - prop= RNA_def_property(srna, "mass", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "nodemass"); - RNA_def_property_range(prop, 0.0f, 50000.0f); - RNA_def_property_ui_text(prop, "Mass", ""); - - prop= RNA_def_property(srna, "gravity", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "grav"); - RNA_def_property_range(prop, -10.0f, 10.0f); - RNA_def_property_ui_text(prop, "Gravitation", "Apply gravitation to point movement"); - - prop= RNA_def_property(srna, "speed", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "physics_speed"); - RNA_def_property_range(prop, 0.01f, 100.0f); - RNA_def_property_ui_text(prop, "Speed", "Tweak timing for physics to control frequency and speed"); - - /* Goal */ - - /*prop= RNA_def_property(srna, "vertex_group", PROP_STRING, PROP_NONE); - RNA_def_property_string_sdna(prop, NULL, "vertgroup"); - RNA_def_property_ui_text(prop, "Vertex Group", "Use control point weight values");*/ - - prop= RNA_def_property(srna, "goal_min", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "mingoal"); - RNA_def_property_range(prop, 0.0f, 1.0f); - RNA_def_property_ui_text(prop, "Goal Minimum", "Goal minimum, vertex group weights are scaled to match this range."); - - prop= RNA_def_property(srna, "goal_max", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "maxgoal"); - RNA_def_property_range(prop, 0.0f, 1.0f); - RNA_def_property_ui_text(prop, "Goal Maximum", "Goal maximum, vertex group weights are scaled to match this range."); - - prop= RNA_def_property(srna, "goal_default", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "defgoal"); - RNA_def_property_range(prop, 0.0f, 1.0f); - RNA_def_property_ui_text(prop, "Goal Default", "Default Goal (vertex target position) value, when no Vertex Group used."); - - prop= RNA_def_property(srna, "goal_spring", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "goalspring"); - RNA_def_property_range(prop, 0.0f, 0.999f); - RNA_def_property_ui_text(prop, "Goal Stiffness", "Goal (vertex target position) spring stiffness."); - - prop= RNA_def_property(srna, "goal_friction", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "goalfrict"); - RNA_def_property_range(prop, 0.0f, 50.0f); - RNA_def_property_ui_text(prop, "Goal Damping", "Goal (vertex target position) friction."); - - /* Edge Spring Settings */ - - prop= RNA_def_property(srna, "pull", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "inspring"); - RNA_def_property_range(prop, 0.0f, 0.999f); - RNA_def_property_ui_text(prop, "Pull", "Edge spring stiffness when longer than rest length"); - - prop= RNA_def_property(srna, "push", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "inpush"); - RNA_def_property_range(prop, 0.0f, 0.999f); - RNA_def_property_ui_text(prop, "Push", "Edge spring stiffness when shorter than rest length"); - - prop= RNA_def_property(srna, "damp", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "infrict"); - RNA_def_property_range(prop, 0.0f, 50.0f); - RNA_def_property_ui_text(prop, "Damp", "Edge spring friction"); - - prop= RNA_def_property(srna, "spring_lenght", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "springpreload"); - RNA_def_property_range(prop, 0.0f, 200.0f); - RNA_def_property_ui_text(prop, "SL", "Alter spring lenght to shrink/blow up (unit %) 0 to disable"); - - prop= RNA_def_property(srna, "aero", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "aeroedge"); - RNA_def_property_range(prop, 0.0f, 30000.0f); - RNA_def_property_ui_text(prop, "Aero", "Make edges 'sail'"); - - prop= RNA_def_property(srna, "plastic", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "plastic"); - RNA_def_property_range(prop, 0.0f, 100.0f); - RNA_def_property_ui_text(prop, "Plastic", "Permanent deform"); - - prop= RNA_def_property(srna, "bending", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "secondspring"); - RNA_def_property_range(prop, 0.0f, 10.0f); - RNA_def_property_ui_text(prop, "Bending", "Bending Stiffness"); - - prop= RNA_def_property(srna, "shear", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "shearstiff"); - RNA_def_property_range(prop, 0.0f, 1.0f); - RNA_def_property_ui_text(prop, "Shear", "Shear Stiffness"); - - /* Collision */ - - prop= RNA_def_property(srna, "collision_type", PROP_ENUM, PROP_NONE); - RNA_def_property_enum_sdna(prop, NULL, "sbc_mode"); - RNA_def_property_enum_items(prop, collision_type_items); - RNA_def_property_ui_text(prop, "Collision Type", "Choose Collision Type"); - - prop= RNA_def_property(srna, "ball_size", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "colball"); - RNA_def_property_range(prop, -10.0f, 10.0f); - RNA_def_property_ui_text(prop, "Ball Size", "Absolute ball size or factor if not manual adjusted"); - - prop= RNA_def_property(srna, "ball_stiff", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "ballstiff"); - RNA_def_property_range(prop, 0.001f, 100.0f); - RNA_def_property_ui_text(prop, "Ball Size", "Ball inflating presure"); - - prop= RNA_def_property(srna, "ball_damp", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "balldamp"); - RNA_def_property_range(prop, 0.001f, 1.0f); - RNA_def_property_ui_text(prop, "Ball Size", "Blending to inelastic collision"); - - /* Solver */ - - prop= RNA_def_property(srna, "error_limit", PROP_FLOAT, PROP_NONE); - RNA_def_property_float_sdna(prop, NULL, "rklimit"); - RNA_def_property_range(prop, 0.001f, 10.0f); - RNA_def_property_ui_text(prop, "Error Limit", "The Runge-Kutta ODE solver error limit, low value gives more precision, high values speed"); - - prop= RNA_def_property(srna, "minstep", PROP_INT, PROP_NONE); - RNA_def_property_int_sdna(prop, NULL, "minloops"); - RNA_def_property_range(prop, 0, 30000); - RNA_def_property_ui_text(prop, "Min Step", "Minimal # solver steps/frame"); - - prop= RNA_def_property(srna, "maxstep", PROP_INT, PROP_NONE); - RNA_def_property_int_sdna(prop, NULL, "maxloops"); - RNA_def_property_range(prop, 0, 30000); - RNA_def_property_ui_text(prop, "Max Step", "Maximal # solver steps/frame"); - - prop= RNA_def_property(srna, "choke", PROP_INT, PROP_NONE); - RNA_def_property_int_sdna(prop, NULL, "choke"); - RNA_def_property_range(prop, 0, 100); - RNA_def_property_ui_text(prop, "Choke", "'Viscosity' inside collision target"); - - prop= RNA_def_property(srna, "fuzzy", PROP_INT, PROP_NONE); - RNA_def_property_int_sdna(prop, NULL, "fuzzyness"); - RNA_def_property_range(prop, 1, 100); - RNA_def_property_ui_text(prop, "Fuzzy", "Fuzzyness while on collision, high values make collsion handling faster but less stable"); - - prop= RNA_def_property(srna, "auto_step", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "solverflags", SBSO_OLDERR); - RNA_def_property_ui_text(prop, "V", "Use velocities for automagic step sizes"); - - prop= RNA_def_property(srna, "diagnose", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "solverflags", SBSO_MONITOR); - RNA_def_property_ui_text(prop, "Print Performance to Console", "Turn on SB diagnose console prints"); - - /* Flags */ - - prop= RNA_def_property(srna, "enabled", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_funcs(prop, "rna_SoftBodySettings_enabled_get", "rna_SoftBodySettings_enabled_set"); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Enable", "Sets object to become soft body."); - - prop= RNA_def_property(srna, "use_goal", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_funcs(prop, "rna_SoftBodySettings_use_goal_get", "rna_SoftBodySettings_use_goal_set"); - RNA_def_property_ui_text(prop, "Use Goal", "Define forces for vertices to stick to animated position."); - - prop= RNA_def_property(srna, "use_edges", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_funcs(prop, "rna_SoftBodySettings_use_edges_get", "rna_SoftBodySettings_use_edges_set"); - RNA_def_property_ui_text(prop, "Use Edges", "Use Edges as springs"); - - prop= RNA_def_property(srna, "stiff_quads", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_funcs(prop, "rna_SoftBodySettings_stiff_quads_get", "rna_SoftBodySettings_stiff_quads_set"); - RNA_def_property_ui_text(prop, "Stiff Quads", "Adds diagonal springs on 4-gons."); - - prop= RNA_def_property(srna, "edge_collision", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_funcs(prop, "rna_SoftBodySettings_edge_collision_get", "rna_SoftBodySettings_edge_collision_set"); - RNA_def_property_ui_text(prop, "Edge Collision", "Edges collide too."); - - prop= RNA_def_property(srna, "face_collision", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_funcs(prop, "rna_SoftBodySettings_face_collision_get", "rna_SoftBodySettings_face_collision_set"); - RNA_def_property_ui_text(prop, "Face Collision", "Faces collide too, SLOOOOOW warning."); - - prop= RNA_def_property(srna, "new_aero", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_funcs(prop, "rna_SoftBodySettings_new_aero_get", "rna_SoftBodySettings_new_aero_set"); - RNA_def_property_ui_text(prop, "N", "New aero(uses angle and length)."); - - prop= RNA_def_property(srna, "self_collision", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_funcs(prop, "rna_SoftBodySettings_self_collision_get", "rna_SoftBodySettings_self_collision_set"); - RNA_def_property_ui_text(prop, "Self Collision", "Enable naive vertex ball self collision."); } void RNA_def_object_force(BlenderRNA *brna) diff --git a/source/blender/makesrna/intern/rna_packedfile.c b/source/blender/makesrna/intern/rna_packedfile.c index 6b9a708f555..6b6db71ef87 100644 --- a/source/blender/makesrna/intern/rna_packedfile.c +++ b/source/blender/makesrna/intern/rna_packedfile.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_packedfile.c 19382 2009-03-23 13:24:48Z blendix $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_particle.c b/source/blender/makesrna/intern/rna_particle.c index d60a215b498..efcd9dbd434 100644 --- a/source/blender/makesrna/intern/rna_particle.c +++ b/source/blender/makesrna/intern/rna_particle.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_particle.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -38,7 +38,6 @@ #include "DNA_scene_types.h" #include "WM_types.h" -#include "WM_api.h" #ifdef RNA_RUNTIME @@ -46,110 +45,48 @@ #include "BKE_depsgraph.h" #include "BKE_particle.h" -#include "BLI_arithb.h" - -/* property update functions */ static void rna_Particle_redo(bContext *C, PointerRNA *ptr) { - Scene *scene = CTX_data_scene(C); ParticleSettings *part; - if(ptr->type==&RNA_ParticleSystem) { - ParticleSystem *psys = (ParticleSystem*)ptr->data; - Object *ob = psys_find_object(scene, psys); - - psys->recalc = PSYS_RECALC_REDO; - - if(ob) - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); - } - else { + if(ptr->type==&RNA_ParticleSystem) + part = ((ParticleSystem*)ptr->data)->part; + else part = ptr->id.data; - psys_flush_particle_settings(scene, part, PSYS_RECALC_REDO); - } + + psys_flush_particle_settings(CTX_data_scene(C), part, PSYS_RECALC_REDO); } static void rna_Particle_reset(bContext *C, PointerRNA *ptr) { - Scene *scene = CTX_data_scene(C); ParticleSettings *part; - - if(ptr->type==&RNA_ParticleSystem) { - ParticleSystem *psys = (ParticleSystem*)ptr->data; - Object *ob = psys_find_object(scene, psys); - - psys->recalc = PSYS_RECALC_RESET; - - if(ob) { - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); - } - } - else { + if(ptr->type==&RNA_ParticleSystem) + part = ((ParticleSystem*)ptr->data)->part; + else part = ptr->id.data; - psys_flush_particle_settings(scene, part, PSYS_RECALC_RESET); - } + + psys_flush_particle_settings(CTX_data_scene(C), part, PSYS_RECALC_RESET|PSYS_RECALC_REDO); } static void rna_Particle_change_type(bContext *C, PointerRNA *ptr) { - Scene *scene = CTX_data_scene(C); ParticleSettings *part; - - if(ptr->type==&RNA_ParticleSystem) { - ParticleSystem *psys = (ParticleSystem*)ptr->data; - Object *ob = psys_find_object(scene, psys); - - psys->recalc = PSYS_RECALC_RESET|PSYS_RECALC_TYPE; - - if(ob) { - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); - } - } - else { + if(ptr->type==&RNA_ParticleSystem) + part = ((ParticleSystem*)ptr->data)->part; + else part = ptr->id.data; - psys_flush_particle_settings(scene, part, PSYS_RECALC_RESET|PSYS_RECALC_TYPE); - } + + psys_flush_particle_settings(CTX_data_scene(C), part, PSYS_RECALC_RESET|PSYS_RECALC_TYPE|PSYS_RECALC_REDO); } static void rna_Particle_redo_child(bContext *C, PointerRNA *ptr) { - Scene *scene = CTX_data_scene(C); ParticleSettings *part; - - if(ptr->type==&RNA_ParticleSystem) { - ParticleSystem *psys = (ParticleSystem*)ptr->data; - Object *ob = psys_find_object(scene, psys); - - psys->recalc = PSYS_RECALC_CHILD; - - if(ob) - DAG_object_flush_update(scene, ob, OB_RECALC_DATA); - } - else { + if(ptr->type==&RNA_ParticleSystem) + part = ((ParticleSystem*)ptr->data)->part; + else part = ptr->id.data; - psys_flush_particle_settings(scene, part, PSYS_RECALC_CHILD); - } -} -static PointerRNA rna_particle_settings_get(PointerRNA *ptr) -{ - Object *ob= (Object*)ptr->id.data; - ParticleSettings *part = psys_get_current(ob)->part; - - return rna_pointer_inherit_refine(ptr, &RNA_ParticleSettings, part); -} - -static void rna_particle_settings_set(PointerRNA *ptr, PointerRNA value) -{ - Object *ob= (Object*)ptr->id.data; - ParticleSystem *psys = psys_get_current(ob); - - if(psys->part) - psys->part->id.us--; - - psys->part = (ParticleSettings *)value.data; - - if(psys->part) - psys->part->id.us++; + psys_flush_particle_settings(CTX_data_scene(C), part, PSYS_RECALC_CHILD); } static void rna_PartSettings_start_set(struct PointerRNA *ptr, float value) { @@ -950,7 +887,7 @@ static void rna_def_particle_settings(BlenderRNA *brna) RNA_def_property_int_sdna(prop, NULL, "disp"); RNA_def_property_range(prop, 0, 100); RNA_def_property_ui_text(prop, "Display", "Percentage of particles to display in 3d view"); - RNA_def_property_update(prop, NC_OBJECT|ND_PARTICLE, "rna_Particle_reset"); + RNA_def_property_update(prop, NC_OBJECT|ND_PARTICLE, "rna_Particle_redo"); prop= RNA_def_property(srna, "material", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "omat"); @@ -1487,9 +1424,14 @@ static void rna_def_particle_settings(BlenderRNA *brna) RNA_def_property_flag(prop, PROP_EDITABLE); RNA_def_property_ui_text(prop, "Billboard Object", "Billboards face this object (default is active camera)"); RNA_def_property_update(prop, NC_OBJECT|ND_PARTICLE, "rna_Particle_redo"); - - /* animation here? */ - rna_def_animdata_common(srna); + +#if 0 + prop= RNA_def_property(srna, "ipo", PROP_POINTER, PROP_NONE); + RNA_def_property_clear_flag(prop, PROP_EDITABLE); + RNA_def_property_pointer_sdna(prop, NULL, "ipo"); + RNA_def_property_struct_type(prop, "Ipo"); + RNA_def_property_ui_text(prop, "Ipo", ""); +#endif // struct PartDeflect *pd; // struct PartDeflect *pd2; @@ -1510,15 +1452,9 @@ static void rna_def_particle_system(BlenderRNA *brna) RNA_def_property_clear_flag(prop, PROP_EDITABLE); RNA_def_struct_name_property(srna, prop); - /* access to particle settings is redirected through functions */ - /* to allow proper id-buttons functionality */ prop= RNA_def_property(srna, "settings", PROP_POINTER, PROP_NEVER_NULL); - //RNA_def_property_pointer_sdna(prop, NULL, "part"); - RNA_def_property_struct_type(prop, "ParticleSettings"); - RNA_def_property_flag(prop, PROP_EDITABLE); - RNA_def_property_pointer_funcs(prop, "rna_particle_settings_get", "rna_particle_settings_set", NULL); + RNA_def_property_pointer_sdna(prop, NULL, "part"); RNA_def_property_ui_text(prop, "Settings", "Particle system settings."); - RNA_def_property_update(prop, NC_OBJECT|ND_PARTICLE, "rna_Particle_reset"); prop= RNA_def_property(srna, "particles", PROP_COLLECTION, PROP_NONE); RNA_def_property_collection_sdna(prop, NULL, "particles", "totpart"); @@ -1733,14 +1669,6 @@ static void rna_def_particle_system(BlenderRNA *brna) RNA_def_property_pointer_sdna(prop, NULL, "pointcache"); RNA_def_property_struct_type(prop, "PointCache"); RNA_def_property_ui_text(prop, "Point Cache", ""); - - /* offset ob */ - prop= RNA_def_property(srna, "parent", PROP_POINTER, PROP_NONE); - RNA_def_property_pointer_sdna(prop, NULL, "parent"); - RNA_def_property_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Parent", "Use this object's coordinate system instead of global coordinate system."); - RNA_def_property_update(prop, NC_OBJECT|ND_PARTICLE, "rna_Particle_redo"); - } void RNA_def_particle(BlenderRNA *brna) diff --git a/source/blender/makesrna/intern/rna_pose.c b/source/blender/makesrna/intern/rna_pose.c index b8863540bdf..54cf1dea0ac 100644 --- a/source/blender/makesrna/intern/rna_pose.c +++ b/source/blender/makesrna/intern/rna_pose.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_pose.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_property.c b/source/blender/makesrna/intern/rna_property.c index a840552b86f..a0a5c41b19c 100644 --- a/source/blender/makesrna/intern/rna_property.c +++ b/source/blender/makesrna/intern/rna_property.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_property.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_radio.c b/source/blender/makesrna/intern/rna_radio.c new file mode 100644 index 00000000000..8b862b4c535 --- /dev/null +++ b/source/blender/makesrna/intern/rna_radio.c @@ -0,0 +1,140 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * Contributor(s): Blender Foundation (2008). + * + * ***** END GPL LICENSE BLOCK ***** + */ + +#include <stdlib.h> + +#include "RNA_define.h" +#include "RNA_types.h" + +#include "rna_internal.h" + +#include "DNA_radio_types.h" + +#ifdef RNA_RUNTIME + +#else + +void RNA_def_radio(BlenderRNA *brna) +{ + StructRNA *srna; + PropertyRNA *prop; + static EnumPropertyItem prop_drawtype_items[] = { + {RAD_WIREFRAME, "WIREFRAME", 0, "Wireframe", "Enables Wireframe draw mode"}, + {RAD_SOLID, "SOLID", 0, "Solid", "Enables Solid draw mode"}, + {RAD_GOURAUD, "GOURAUD", 0, "Gouraud", "Enables Gouraud draw mode"}, + {0, NULL, 0, NULL, NULL}}; + + srna= RNA_def_struct(brna, "Radiosity", NULL); + RNA_def_struct_ui_text(srna, "Radiosity", "Settings for radiosity simulation of indirect diffuse lighting."); + RNA_def_struct_sdna(srna, "Radio"); + + /* Enums */ + prop= RNA_def_property(srna, "draw_mode", PROP_ENUM, PROP_NONE); + RNA_def_property_enum_sdna(prop, NULL, "drawtype"); + RNA_def_property_enum_items(prop, prop_drawtype_items); + RNA_def_property_ui_text(prop, "Draw Mode", "Radiosity draw modes."); + + /* Number values */ + prop= RNA_def_property(srna, "hemi_resolution", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "hemires"); + RNA_def_property_range(prop, 100, 1000); + RNA_def_property_ui_text(prop, "Hemi Resolution", "Sets the size of a hemicube."); + + prop= RNA_def_property(srna, "max_iterations", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "maxiter"); + RNA_def_property_range(prop, 0, 10000); + RNA_def_property_ui_text(prop, "Max Iterations", "Limits the maximum number of radiosity rounds."); + + prop= RNA_def_property(srna, "multiplier", PROP_FLOAT, PROP_NONE); + RNA_def_property_float_sdna(prop, NULL, "radfac"); + RNA_def_property_range(prop, 0.001f, 250.0f); + RNA_def_property_ui_text(prop, "Multiplier", "Multiplies the energy values."); + + prop= RNA_def_property(srna, "gamma", PROP_FLOAT, PROP_NONE); + RNA_def_property_float_sdna(prop, NULL, "gamma"); + RNA_def_property_range(prop, 0.2f, 10.0f); + RNA_def_property_ui_text(prop, "Gamma", "Changes the contrast of the energy values."); + + prop= RNA_def_property(srna, "convergence", PROP_FLOAT, PROP_NONE); + RNA_def_property_float_sdna(prop, NULL, "convergence"); + RNA_def_property_range(prop, 0.0f, 1.0f); + RNA_def_property_ui_text(prop, "Convergence", "Sets the lower threshold of unshot energy."); + + prop= RNA_def_property(srna, "element_max", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "elma"); + RNA_def_property_range(prop, 1, 500); + RNA_def_property_ui_text(prop, "Element Max", "Sets maximum size of an element"); + + prop= RNA_def_property(srna, "element_min", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "elmi"); + RNA_def_property_range(prop, 1, 100); + RNA_def_property_ui_text(prop, "Element Min", "Sets minimum size of an element"); + + prop= RNA_def_property(srna, "patch_max", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "pama"); + RNA_def_property_range(prop, 10, 1000); + RNA_def_property_ui_text(prop, "Patch Max", "Sets maximum size of a patch."); + + prop= RNA_def_property(srna, "patch_min", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "pami"); + RNA_def_property_range(prop, 10, 1000); + RNA_def_property_ui_text(prop, "Patch Min", "Sets minimum size of a patch."); + + prop= RNA_def_property(srna, "subshoot_patch", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "subshootp"); + RNA_def_property_range(prop, 0, 10); + RNA_def_property_ui_text(prop, "SubShoot Patch", "Sets the number of times the environment is tested to detect paths."); + + prop= RNA_def_property(srna, "subshoot_element", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "subshoote"); + RNA_def_property_range(prop, 0, 10); + RNA_def_property_ui_text(prop, "SubShoot Element", "Sets the number of times the environment is tested to detect elements."); + + prop= RNA_def_property(srna, "max_elements", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "maxnode"); + RNA_def_property_range(prop, 1, 250000); + RNA_def_property_ui_text(prop, "Max Elements", "Sets the maximum allowed number of elements."); + + prop= RNA_def_property(srna, "max_subdiv_shoot", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "maxsublamp"); + RNA_def_property_range(prop, 1, 250); + RNA_def_property_ui_text(prop, "Max Subdiv Shoot", "Sets the maximum number of initial shoot patches that are evaluated"); + + prop= RNA_def_property(srna, "remove_doubles_limit", PROP_INT, PROP_NONE); + RNA_def_property_int_sdna(prop, NULL, "nodelim"); + RNA_def_property_range(prop, 0, 50); + RNA_def_property_ui_text(prop, "Remove Doubles Limit", "Sets the range for removing doubles"); + + /* flag */ + prop= RNA_def_property(srna, "show_limits", PROP_BOOLEAN, PROP_NONE); + RNA_def_property_boolean_sdna(prop, NULL, "flag", RAD_SHOWLIMITS); + RNA_def_property_ui_text(prop, "Show Limits", "Draws patch and element limits"); + + prop= RNA_def_property(srna, "show_z", PROP_BOOLEAN, PROP_NONE); + RNA_def_property_boolean_sdna(prop, NULL, "flag", RAD_SHOWZ); + RNA_def_property_ui_text(prop, "Show Z", "Draws limits differently"); +} + +#endif + diff --git a/source/blender/makesrna/intern/rna_rna.c b/source/blender/makesrna/intern/rna_rna.c index 14db8ea3377..5066654434e 100644 --- a/source/blender/makesrna/intern/rna_rna.c +++ b/source/blender/makesrna/intern/rna_rna.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_rna.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -309,16 +309,14 @@ PointerRNA rna_builtin_properties_lookup_string(PointerRNA *ptr, const char *key } } while((srna=srna->base)); - if(ptr->data) { - group= RNA_struct_idproperties(ptr, 0); + group= RNA_struct_idproperties(ptr, 0); - if(group) { - for(idp=group->data.group.first; idp; idp=idp->next) { - if(strcmp(idp->name, key) == 0) { - propptr.type= &RNA_Property; - propptr.data= idp; - return propptr; - } + if(group) { + for(idp=group->data.group.first; idp; idp=idp->next) { + if(strcmp(idp->name, key) == 0) { + propptr.type= &RNA_Property; + propptr.data= idp; + return propptr; } } } diff --git a/source/blender/makesrna/intern/rna_scene.c b/source/blender/makesrna/intern/rna_scene.c index fd146acc6fe..875d657dee4 100644 --- a/source/blender/makesrna/intern/rna_scene.c +++ b/source/blender/makesrna/intern/rna_scene.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_scene.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -151,34 +151,8 @@ void rna_def_tool_settings(BlenderRNA *brna) StructRNA *srna; PropertyRNA *prop; - static EnumPropertyItem uv_select_mode_items[] = { - {UV_SELECT_VERTEX, "VERTEX", ICON_VERTEXSEL, "Vertex", "Vertex selection mode."}, - {UV_SELECT_EDGE, "EDGE", ICON_EDGESEL, "Edge", "Edge selection mode."}, - {UV_SELECT_FACE, "FACE", ICON_FACESEL, "Face", "Face selection mode."}, - {UV_SELECT_ISLAND, "ISLAND", ICON_LINKEDSEL, "Island", "Island selection mode."}, - {0, NULL, 0, NULL, NULL}}; - - static EnumPropertyItem mesh_select_mode_items[] = { - {SCE_SELECT_VERTEX, "VERTEX", ICON_VERTEXSEL, "Vertex", "Vertex selection mode."}, - {SCE_SELECT_EDGE, "EDGE", ICON_EDGESEL, "Edge", "Edge selection mode."}, - {SCE_SELECT_FACE, "FACE", ICON_FACESEL, "Face", "Face selection mode."}, - {0, NULL, 0, NULL, NULL}}; - - static EnumPropertyItem snap_element_items[] = { - {SCE_SNAP_MODE_VERTEX, "VERTEX", ICON_SNAP_VERTEX, "Vertex", "Snap to vertices."}, - {SCE_SNAP_MODE_EDGE, "EDGE", ICON_SNAP_EDGE, "Edge", "Snap to edges."}, - {SCE_SNAP_MODE_FACE, "FACE", ICON_SNAP_FACE, "Face", "Snap to faces."}, - {SCE_SNAP_MODE_VOLUME, "VOLUME", ICON_SNAP_VOLUME, "Volume", "Snap to volume."}, - {0, NULL, 0, NULL, NULL}}; - - static EnumPropertyItem snap_mode_items[] = { - {SCE_SNAP_TARGET_CLOSEST, "CLOSEST", 0, "Closest", "Snap closest point onto target."}, - {SCE_SNAP_TARGET_CENTER, "CENTER", 0, "Center", "Snap center onto target."}, - {SCE_SNAP_TARGET_MEDIAN, "MEDIAN", 0, "Median", "Snap median onto target."}, - {SCE_SNAP_TARGET_ACTIVE, "ACTIVE", 0, "Active", "Snap active onto target."}, - {0, NULL, 0, NULL, NULL}}; - srna= RNA_def_struct(brna, "ToolSettings", NULL); + RNA_def_struct_nested(brna, srna, "Scene"); RNA_def_struct_ui_text(srna, "Tool Settings", ""); prop= RNA_def_property(srna, "sculpt", PROP_POINTER, PROP_NONE); @@ -189,62 +163,6 @@ void rna_def_tool_settings(BlenderRNA *brna) RNA_def_property_struct_type(prop, "VPaint"); RNA_def_property_ui_text(prop, "Vertex Paint", ""); - /* Transform */ - prop= RNA_def_property(srna, "proportional_editing", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "proportional", 0); - RNA_def_property_ui_text(prop, "Proportional Editing", "Proportional editing mode."); - - prop= RNA_def_property(srna, "proportional_editing_falloff", PROP_ENUM, PROP_NONE); - RNA_def_property_enum_sdna(prop, NULL, "prop_mode"); - RNA_def_property_enum_items(prop, prop_mode_items); - RNA_def_property_ui_text(prop, "Proportional Editing Falloff", "Falloff type for proportional editing mode."); - - prop= RNA_def_property(srna, "snap", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "snap_flag", SCE_SNAP); - RNA_def_property_ui_text(prop, "Snap", "Snap while Ctrl is held during transform."); - RNA_def_property_ui_icon(prop, ICON_SNAP_GEAR, 1); - - prop= RNA_def_property(srna, "snap_align_rotation", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "snap_flag", SCE_SNAP_ROTATE); - RNA_def_property_ui_text(prop, "Snap Align Rotation", "Align rotation with the snapping target."); - RNA_def_property_ui_icon(prop, ICON_SNAP_NORMAL, 0); - - prop= RNA_def_property(srna, "snap_element", PROP_ENUM, PROP_NONE); - RNA_def_property_enum_sdna(prop, NULL, "snap_mode"); - RNA_def_property_enum_items(prop, snap_element_items); - RNA_def_property_ui_text(prop, "Snap Element", "Type of element to snap to."); - - prop= RNA_def_property(srna, "snap_mode", PROP_ENUM, PROP_NONE); - RNA_def_property_enum_sdna(prop, NULL, "snap_target"); - RNA_def_property_enum_items(prop, snap_mode_items); - RNA_def_property_ui_text(prop, "Snap Mode", "Which part to snap onto the target."); - - prop= RNA_def_property(srna, "snap_peel_object", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "snap_flag", SCE_SNAP_PEEL_OBJECT); - RNA_def_property_ui_text(prop, "Snap Peel Object", "Consider objects as whole when finding volume center."); - RNA_def_property_ui_icon(prop, ICON_SNAP_PEEL_OBJECT, 0); - - /* UV */ - prop= RNA_def_property(srna, "uv_selection_mode", PROP_ENUM, PROP_NONE); - RNA_def_property_enum_sdna(prop, NULL, "uv_selectmode"); - RNA_def_property_enum_items(prop, uv_select_mode_items); - RNA_def_property_ui_text(prop, "UV Selection Mode", "UV selection and display mode."); - - prop= RNA_def_property(srna, "uv_sync_selection", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "uv_flag", UV_SYNC_SELECTION); - RNA_def_property_ui_text(prop, "UV Sync Selection", "Keep UV and edit mode mesh selection in sync."); - RNA_def_property_ui_icon(prop, ICON_EDIT, 0); - - prop= RNA_def_property(srna, "uv_local_view", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "uv_flag", UV_SHOW_SAME_IMAGE); - RNA_def_property_ui_text(prop, "UV Local View", "Draw only faces with the currently displayed image assigned."); - - /* Mesh */ - prop= RNA_def_property(srna, "mesh_selection_mode", PROP_ENUM, PROP_NONE); - RNA_def_property_enum_bitflag_sdna(prop, NULL, "selectmode"); - RNA_def_property_enum_items(prop, mesh_select_mode_items); - RNA_def_property_ui_text(prop, "Mesh Selection Mode", "Mesh selection and display mode."); - rna_def_sculpt(brna); } @@ -934,6 +852,10 @@ void RNA_def_scene(BlenderRNA *brna) { StructRNA *srna; PropertyRNA *prop; + static EnumPropertyItem unwrapper_items[] = { + {0, "CONFORMAL", 0, "Conformal", ""}, + {1, "ANGLEBASED", 0, "Angle Based", ""}, + {0, NULL, 0, NULL, NULL}}; srna= RNA_def_struct(brna, "Scene", "ID"); RNA_def_struct_ui_text(srna, "Scene", "Scene consisting objects and defining time and render related settings."); @@ -965,6 +887,11 @@ void RNA_def_scene(BlenderRNA *brna) RNA_def_property_ui_text(prop, "Visible Layers", "Layers visible when rendering the scene."); RNA_def_property_boolean_funcs(prop, NULL, "rna_Scene_layer_set"); + prop= RNA_def_property(srna, "proportional_editing_falloff", PROP_ENUM, PROP_NONE); + RNA_def_property_enum_sdna(prop, NULL, "prop_mode"); + RNA_def_property_enum_items(prop, prop_mode_items); + RNA_def_property_ui_text(prop, "Proportional Editing Falloff", "Falloff type for proportional editing mode."); + prop= RNA_def_property(srna, "current_frame", PROP_INT, PROP_NONE); RNA_def_property_clear_flag(prop, PROP_ANIMATEABLE); RNA_def_property_int_sdna(prop, NULL, "r.cfra"); @@ -997,6 +924,11 @@ void RNA_def_scene(BlenderRNA *brna) RNA_def_property_ui_text(prop, "Stamp Note", "User define note for the render stamping."); RNA_def_property_update(prop, NC_SCENE|ND_RENDER_OPTIONS, NULL); + prop= RNA_def_property(srna, "unwrapper", PROP_ENUM, PROP_NONE); + RNA_def_property_enum_sdna(prop, NULL, "toolsettings->unwrapper"); + RNA_def_property_enum_items(prop, unwrapper_items); + RNA_def_property_ui_text(prop, "Unwrapper", "Unwrap algorithm used by the Unwrap tool."); + prop= RNA_def_property(srna, "nodetree", PROP_POINTER, PROP_NONE); RNA_def_property_ui_text(prop, "Node Tree", "Compositing node tree."); @@ -1004,6 +936,10 @@ void RNA_def_scene(BlenderRNA *brna) RNA_def_property_pointer_sdna(prop, NULL, "ed"); RNA_def_property_struct_type(prop, "SequenceEditor"); RNA_def_property_ui_text(prop, "Sequence Editor", ""); + + prop= RNA_def_property(srna, "radiosity", PROP_POINTER, PROP_NONE); + RNA_def_property_pointer_sdna(prop, NULL, "radio"); + RNA_def_property_ui_text(prop, "Radiosity", ""); prop= RNA_def_property(srna, "keyingsets", PROP_COLLECTION, PROP_NONE); RNA_def_property_collection_sdna(prop, NULL, "keyingsets", NULL); diff --git a/source/blender/makesrna/intern/rna_screen.c b/source/blender/makesrna/intern/rna_screen.c index b7279757455..35191744f22 100644 --- a/source/blender/makesrna/intern/rna_screen.c +++ b/source/blender/makesrna/intern/rna_screen.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_screen.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_scriptlink.c b/source/blender/makesrna/intern/rna_scriptlink.c index b486cd4a874..db33e7a8543 100644 --- a/source/blender/makesrna/intern/rna_scriptlink.c +++ b/source/blender/makesrna/intern/rna_scriptlink.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_scriptlink.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_sensor.c b/source/blender/makesrna/intern/rna_sensor.c index 53bd230870f..d31ec7b9b83 100644 --- a/source/blender/makesrna/intern/rna_sensor.c +++ b/source/blender/makesrna/intern/rna_sensor.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_sensor.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_sequence.c b/source/blender/makesrna/intern/rna_sequence.c index 055e67fb135..5b76db4ff43 100644 --- a/source/blender/makesrna/intern/rna_sequence.c +++ b/source/blender/makesrna/intern/rna_sequence.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_sequence.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_sound.c b/source/blender/makesrna/intern/rna_sound.c index 363a5595b43..f26024f7a9e 100644 --- a/source/blender/makesrna/intern/rna_sound.c +++ b/source/blender/makesrna/intern/rna_sound.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_sound.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_space.c b/source/blender/makesrna/intern/rna_space.c index d5ac0d6e427..12f0c110ea2 100644 --- a/source/blender/makesrna/intern/rna_space.c +++ b/source/blender/makesrna/intern/rna_space.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_space.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -246,10 +246,19 @@ static void rna_def_space_image_uv(BlenderRNA *brna) StructRNA *srna; PropertyRNA *prop; +#if 0 + static EnumPropertyItem select_mode_items[] = { + {SI_SELECT_VERTEX, "VERTEX", 0, "Vertex", "Vertex selection mode."}, + //{SI_SELECT_EDGE, "Edge", 0, "Edge", "Edge selection mode."}, + {SI_SELECT_FACE, "FACE", 0, "Face", "Face selection mode."}, + {SI_SELECT_ISLAND, "ISLAND", 0, "Island", "Island selection mode."}, + {0, NULL, 0, NULL, NULL}}; +#endif + static EnumPropertyItem sticky_mode_items[] = { - {SI_STICKY_DISABLE, "DISABLED", ICON_STICKY_UVS_DISABLE, "Disabled", "Sticky vertex selection disabled."}, - {SI_STICKY_LOC, "SHARED_LOCATION", ICON_STICKY_UVS_LOC, "SHARED_LOCATION", "Select UVs that are at the same location and share a mesh vertex."}, - {SI_STICKY_VERTEX, "SHARED_VERTEX", ICON_STICKY_UVS_VERT, "SHARED_VERTEX", "Select UVs that share mesh vertex, irrespective if they are in the same location."}, + {SI_STICKY_DISABLE, "DISABLED", 0, "Disabled", "Sticky vertex selection disabled."}, + {SI_STICKY_LOC, "SHARED_LOCATION", 0, "SHARED_LOCATION", "Select UVs that are at the same location and share a mesh vertex."}, + {SI_STICKY_VERTEX, "SHARED_VERTEX", 0, "SHARED_VERTEX", "Select UVs that share mesh vertex, irrespective if they are in the same location."}, {0, NULL, 0, NULL, NULL}}; static EnumPropertyItem dt_uv_items[] = { @@ -264,18 +273,17 @@ static void rna_def_space_image_uv(BlenderRNA *brna) {SI_UVDT_STRETCH_AREA, "AREA", 0, "Area", "Area distortion between UV and 3D faces."}, {0, NULL, 0, NULL, NULL}}; - static EnumPropertyItem pivot_items[] = { - {V3D_CENTER, "CENTER", ICON_ROTATE, "Bounding Box Center", ""}, - {V3D_CENTROID, "MEDIAN", ICON_ROTATECENTER, "Median Point", ""}, - {V3D_CURSOR, "CURSOR", ICON_CURSOR, "2D Cursor", ""}, - {0, NULL, 0, NULL, NULL}}; - srna= RNA_def_struct(brna, "SpaceUVEditor", NULL); RNA_def_struct_sdna(srna, "SpaceImage"); RNA_def_struct_nested(brna, srna, "SpaceImageEditor"); RNA_def_struct_ui_text(srna, "Space UV Editor", "UV editor data for the image editor space."); /* selection */ + /*prop= RNA_def_property(srna, "selection_mode", PROP_ENUM, PROP_NONE); + RNA_def_property_enum_sdna(prop, NULL, "selectmode"); + RNA_def_property_enum_items(prop, select_mode_items); + RNA_def_property_ui_text(prop, "Selection Mode", "UV selection and display mode.");*/ + prop= RNA_def_property(srna, "sticky_selection_mode", PROP_ENUM, PROP_NONE); RNA_def_property_enum_sdna(prop, NULL, "sticky"); RNA_def_property_enum_items(prop, sticky_mode_items); @@ -305,15 +313,16 @@ static void rna_def_space_image_uv(BlenderRNA *brna) RNA_def_property_ui_text(prop, "Draw Stretch Type", "Type of stretch to draw."); RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); - prop= RNA_def_property(srna, "draw_modified_edges", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "flag", SI_DRAWSHADOW); - RNA_def_property_ui_text(prop, "Draw Modified Edges", "Draw edges after modifiers are applied."); + prop= RNA_def_property(srna, "draw_modified_edges", PROP_ENUM, PROP_NONE); + RNA_def_property_enum_sdna(prop, NULL, "dt_uvstretch"); + RNA_def_property_enum_items(prop, dt_uvstretch_items); + RNA_def_property_ui_text(prop, "Draw Modified Edges", "Draw edges from the final mesh after object modifier evaluation."); RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); - prop= RNA_def_property(srna, "draw_other_objects", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "flag", SI_DRAW_OTHER); - RNA_def_property_ui_text(prop, "Draw Other Objects", "Draw other selected objects that share the same image."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); + /*prop= RNA_def_property(srna, "local_view", PROP_BOOLEAN, PROP_NONE); + RNA_def_property_boolean_sdna(prop, NULL, "flag", SI_LOCAL_UV); + RNA_def_property_ui_text(prop, "Local View", "Draw only faces with the currently displayed image assigned."); + RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL);*/ prop= RNA_def_property(srna, "normalized_coordinates", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flag", SI_COORDFLOATS); @@ -322,6 +331,12 @@ static void rna_def_space_image_uv(BlenderRNA *brna) /* todo: move edge and face drawing options here from G.f */ + /* editing */ + /*prop= RNA_def_property(srna, "sync_selection", PROP_BOOLEAN, PROP_NONE); + RNA_def_property_boolean_sdna(prop, NULL, "flag", SI_SYNC_UVSEL); + RNA_def_property_ui_text(prop, "Sync Selection", "Keep UV and edit mode mesh selection in sync."); + RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL);*/ + prop= RNA_def_property(srna, "snap_to_pixels", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flag", SI_PIXELSNAP); RNA_def_property_ui_text(prop, "Snap to Pixels", "Snap UVs to pixel locations while editing."); @@ -333,12 +348,6 @@ static void rna_def_space_image_uv(BlenderRNA *brna) prop= RNA_def_property(srna, "live_unwrap", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "flag", SI_LIVE_UNWRAP); RNA_def_property_ui_text(prop, "Live Unwrap", "Continuously unwrap the selected UV island while transforming pinned vertices."); - - prop= RNA_def_property(srna, "pivot", PROP_ENUM, PROP_NONE); - RNA_def_property_enum_sdna(prop, NULL, "around"); - RNA_def_property_enum_items(prop, pivot_items); - RNA_def_property_ui_text(prop, "Pivot", "Rotation/Scaling Pivot."); - RNA_def_property_update(prop, NC_IMAGE|ND_DISPLAY, NULL); } static void rna_def_space_outliner(BlenderRNA *brna) @@ -566,17 +575,18 @@ static void rna_def_space_buttons(BlenderRNA *brna) PropertyRNA *prop; static EnumPropertyItem buttons_context_items[] = { - {BCONTEXT_SCENE, "SCENE", ICON_SCENE, "Scene", "Scene"}, - {BCONTEXT_WORLD, "WORLD", ICON_WORLD, "World", "World"}, - {BCONTEXT_OBJECT, "OBJECT", ICON_OBJECT_DATA, "Object", "Object"}, - {BCONTEXT_CONSTRAINT, "CONSTRAINT", ICON_CONSTRAINT, "Constraint", "Constraint"}, - {BCONTEXT_MODIFIER, "MODIFIER", ICON_MODIFIER, "Modifier", "Modifier"}, - {BCONTEXT_DATA, "DATA", 0, "Data", "Data"}, - {BCONTEXT_BONE, "BONE", ICON_BONE_DATA, "Bone", "Bone"}, - {BCONTEXT_MATERIAL, "MATERIAL", ICON_MATERIAL, "Material", "Material"}, - {BCONTEXT_TEXTURE, "TEXTURE", ICON_TEXTURE, "Texture", "Texture"}, - {BCONTEXT_PARTICLE, "PARTICLE", ICON_PARTICLES, "Particle", "Particle"}, - {BCONTEXT_PHYSICS, "PHYSICS", ICON_PHYSICS, "Physics", "Physics"}, + {BCONTEXT_SCENE, "SCENE", 0, "Scene", ""}, + {BCONTEXT_WORLD, "WORLD", 0, "World", ""}, + {BCONTEXT_OBJECT, "OBJECT", 0, "Object", ""}, + {BCONTEXT_DATA, "DATA", 0, "Data", ""}, + {BCONTEXT_MATERIAL, "MATERIAL", 0, "Material", ""}, + {BCONTEXT_TEXTURE, "TEXTURE", 0, "Texture", ""}, + {BCONTEXT_PARTICLE, "PARTICLE", 0, "Particle", ""}, + {BCONTEXT_PHYSICS, "PHYSICS", 0, "Physics", ""}, + {BCONTEXT_GAME, "GAME", 0, "Game", ""}, + {BCONTEXT_BONE, "BONE", 0, "Bone", ""}, + {BCONTEXT_MODIFIER, "MODIFIER", 0, "Modifier", ""}, + {BCONTEXT_CONSTRAINT, "CONSTRAINT", 0, "Constraint", ""}, {0, NULL, 0, NULL, NULL}}; static EnumPropertyItem panel_alignment_items[] = { @@ -592,13 +602,11 @@ static void rna_def_space_buttons(BlenderRNA *brna) RNA_def_property_enum_sdna(prop, NULL, "mainb"); RNA_def_property_enum_items(prop, buttons_context_items); RNA_def_property_ui_text(prop, "Buttons Context", "The type of active data to display and edit in the buttons window"); - RNA_def_property_update(prop, NC_WINDOW, NULL); prop= RNA_def_property(srna, "panel_alignment", PROP_ENUM, PROP_NONE); RNA_def_property_enum_sdna(prop, NULL, "align"); RNA_def_property_enum_items(prop, panel_alignment_items); RNA_def_property_ui_text(prop, "Panel Alignment", "Arrangement of the panels within the buttons window"); - RNA_def_property_update(prop, NC_WINDOW, NULL); /* pinned data */ prop= RNA_def_property(srna, "pin_id", PROP_POINTER, PROP_NONE); diff --git a/source/blender/makesrna/intern/rna_text.c b/source/blender/makesrna/intern/rna_text.c index cd39c317bc5..b44c392d741 100644 --- a/source/blender/makesrna/intern/rna_text.c +++ b/source/blender/makesrna/intern/rna_text.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_text.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_texture.c b/source/blender/makesrna/intern/rna_texture.c index 2a7f65e2d90..33d7c8fd6c0 100644 --- a/source/blender/makesrna/intern/rna_texture.c +++ b/source/blender/makesrna/intern/rna_texture.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_texture.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_timeline.c b/source/blender/makesrna/intern/rna_timeline.c index d42603e1952..deb40f85986 100644 --- a/source/blender/makesrna/intern/rna_timeline.c +++ b/source/blender/makesrna/intern/rna_timeline.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_timeline.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_ui.c b/source/blender/makesrna/intern/rna_ui.c index 825b3711b97..976ccc670bb 100644 --- a/source/blender/makesrna/intern/rna_ui.c +++ b/source/blender/makesrna/intern/rna_ui.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_ui.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_ui_api.c b/source/blender/makesrna/intern/rna_ui_api.c index a4aa60775f2..d06d4d4406d 100644 --- a/source/blender/makesrna/intern/rna_ui_api.c +++ b/source/blender/makesrna/intern/rna_ui_api.c @@ -136,14 +136,6 @@ void RNA_api_ui_layout(StructRNA *srna) parm= RNA_def_string(func, "value", "", 0, "", "Enum property value."); RNA_def_property_flag(parm, PROP_REQUIRED);*/ - func= RNA_def_function(srna, "item_pointerR", "uiItemPointerR"); - api_ui_item_common(func); - api_ui_item_rna_common(func); - parm= RNA_def_pointer(func, "search_data", "AnyType", "", "Data from which to take collection to search in."); - RNA_def_property_flag(parm, PROP_REQUIRED|PROP_RNAPTR); - parm= RNA_def_string(func, "search_property", "", 0, "", "Identifier of search collection property."); - RNA_def_property_flag(parm, PROP_REQUIRED); - func= RNA_def_function(srna, "itemO", "uiItemO"); api_ui_item_op_common(func); @@ -197,7 +189,8 @@ void RNA_api_ui_layout(StructRNA *srna) api_ui_item_common(func); func= RNA_def_function(srna, "itemM", "uiItemM"); - RNA_def_function_flag(func, FUNC_USE_CONTEXT); + parm= RNA_def_pointer(func, "context", "Context", "", "Current context."); + RNA_def_property_flag(parm, PROP_REQUIRED); api_ui_item_common(func); parm= RNA_def_string(func, "menu", "", 0, "", "Identifier of the menu."); RNA_def_property_flag(parm, PROP_REQUIRED); @@ -213,12 +206,15 @@ void RNA_api_ui_layout(StructRNA *srna) /* templates */ func= RNA_def_function(srna, "template_header", "uiTemplateHeader"); - RNA_def_function_flag(func, FUNC_USE_CONTEXT); + parm= RNA_def_pointer(func, "context", "Context", "", "Current context."); + RNA_def_property_flag(parm, PROP_REQUIRED); func= RNA_def_function(srna, "template_ID", "uiTemplateID"); - RNA_def_function_flag(func, FUNC_USE_CONTEXT); + parm= RNA_def_pointer(func, "context", "Context", "", "Current context."); + RNA_def_property_flag(parm, PROP_REQUIRED); api_ui_item_rna_common(func); RNA_def_string(func, "new", "", 0, "", "Operator identifier to create a new ID block."); + RNA_def_string(func, "open", "", 0, "", "Operator identifier to open a new ID block."); RNA_def_string(func, "unlink", "", 0, "", "Operator identifier to unlink the ID block."); func= RNA_def_function(srna, "template_modifier", "uiTemplateModifier"); @@ -249,23 +245,6 @@ void RNA_api_ui_layout(StructRNA *srna) func= RNA_def_function(srna, "template_layers", "uiTemplateLayers"); api_ui_item_rna_common(func); - - func= RNA_def_function(srna, "template_image_layers", "uiTemplateImageLayers"); - RNA_def_function_flag(func, FUNC_USE_CONTEXT); - parm= RNA_def_pointer(func, "image", "Image", "", ""); - RNA_def_property_flag(parm, PROP_REQUIRED); - parm= RNA_def_pointer(func, "image_user", "ImageUser", "", ""); - RNA_def_property_flag(parm, PROP_REQUIRED); - - func= RNA_def_function(srna, "template_list", "uiTemplateList"); - api_ui_item_rna_common(func); - parm= RNA_def_string(func, "active_property", "", 0, "", "Identifier of property in data, for the active element."); - RNA_def_property_flag(parm, PROP_REQUIRED); - parm= RNA_def_int(func, "rows", 5, 0, INT_MAX, "", "Number of rows to display.", 0, INT_MAX); - parm= RNA_def_int(func, "columns", 5, 0, INT_MAX, "", "Number of columns to display.", 0, INT_MAX); - parm= RNA_def_boolean(func, "compact", 0, "", "Use compact, single row list template."); - parm= RNA_def_collection(func, "items", 0, "", "Items visible in the list."); - RNA_def_function_return(func, parm); } #endif diff --git a/source/blender/makesrna/intern/rna_userdef.c b/source/blender/makesrna/intern/rna_userdef.c index 609082144e1..ad3875280fb 100644 --- a/source/blender/makesrna/intern/rna_userdef.c +++ b/source/blender/makesrna/intern/rna_userdef.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_userdef.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -139,12 +139,7 @@ static void rna_def_userdef_theme_ui_font_style(BlenderRNA *brna) prop= RNA_def_property(srna, "kerning", PROP_FLOAT, PROP_NONE); RNA_def_property_range(prop, -5.0, 5.0); - RNA_def_property_ui_text(prop, "Kerning", "User kerning value in pixels"); - RNA_def_property_update(prop, NC_WINDOW, NULL); - - prop= RNA_def_property(srna, "overlap", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "overlap", 1); - RNA_def_property_ui_text(prop, "Overlap", "Check for overlap characters"); + RNA_def_property_ui_text(prop, "Kerning", ""); RNA_def_property_update(prop, NC_WINDOW, NULL); prop= RNA_def_property(srna, "shadow", PROP_INT, PROP_NONE); @@ -306,12 +301,6 @@ static void rna_def_userdef_theme_ui(BlenderRNA *brna) RNA_def_property_struct_type(prop, "ThemeWidgetColors"); RNA_def_property_ui_text(prop, "Option Widget Colors", ""); RNA_def_property_update(prop, NC_WINDOW, NULL); - - prop= RNA_def_property(srna, "wcol_toggle", PROP_POINTER, PROP_NEVER_NULL); - RNA_def_property_pointer_sdna(prop, NULL, "wcol_toggle"); - RNA_def_property_struct_type(prop, "ThemeWidgetColors"); - RNA_def_property_ui_text(prop, "Toggle Widget Colors", ""); - RNA_def_property_update(prop, NC_WINDOW, NULL); prop= RNA_def_property(srna, "wcol_num", PROP_POINTER, PROP_NEVER_NULL); RNA_def_property_pointer_sdna(prop, NULL, "wcol_num"); @@ -354,12 +343,7 @@ static void rna_def_userdef_theme_ui(BlenderRNA *brna) RNA_def_property_struct_type(prop, "ThemeWidgetColors"); RNA_def_property_ui_text(prop, "Menu Item Colors", ""); RNA_def_property_update(prop, NC_WINDOW, NULL); - - prop= RNA_def_property(srna, "wcol_scroll", PROP_POINTER, PROP_NEVER_NULL); - RNA_def_property_pointer_sdna(prop, NULL, "wcol_scroll"); - RNA_def_property_struct_type(prop, "ThemeWidgetColors"); - RNA_def_property_ui_text(prop, "Scroll Widget Colors", ""); - RNA_def_property_update(prop, NC_WINDOW, NULL); + prop= RNA_def_property(srna, "icon_file", PROP_STRING, PROP_FILEPATH); RNA_def_property_string_sdna(prop, NULL, "iconfile"); @@ -1521,7 +1505,7 @@ static void rna_def_userdef_view(BlenderRNA *brna) RNA_def_property_ui_text(prop, "Toolbox Column Layout", "Use a column layout for toolbox."); prop= RNA_def_property(srna, "directional_menus", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_negative_sdna(prop, NULL, "uiflag", USER_MENUFIXEDORDER); + RNA_def_property_boolean_sdna(prop, NULL, "uiflag", USER_DIRECTIONALORDER); RNA_def_property_ui_text(prop, "Contents Follow Opening Direction", "Otherwise menus, etc will always be top to bottom, left to right, no matter opening direction."); /* snap to grid */ diff --git a/source/blender/makesrna/intern/rna_vfont.c b/source/blender/makesrna/intern/rna_vfont.c index aa2aaaf6342..7837a0b5657 100644 --- a/source/blender/makesrna/intern/rna_vfont.c +++ b/source/blender/makesrna/intern/rna_vfont.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_vfont.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_vpaint.c b/source/blender/makesrna/intern/rna_vpaint.c index a34099dffb7..6a831467487 100644 --- a/source/blender/makesrna/intern/rna_vpaint.c +++ b/source/blender/makesrna/intern/rna_vpaint.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_vpaint.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_wm.c b/source/blender/makesrna/intern/rna_wm.c index 1bfc3b6f8f6..3cb3f4ee4cb 100644 --- a/source/blender/makesrna/intern/rna_wm.c +++ b/source/blender/makesrna/intern/rna_wm.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_wm.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -30,120 +30,6 @@ #include "rna_internal.h" #include "DNA_windowmanager_types.h" -#include "WM_types.h" /* wmEvent */ - - -EnumPropertyItem event_value_items[] = { - {KM_ANY, "ANY", 0, "Any", ""}, - {KM_NOTHING, "NOTHING", 0, "Nothing", ""}, - {KM_PRESS, "PRESS", 0, "Press", ""}, - {KM_RELEASE, "RELEASE", 0, "Release", ""}, - {0, NULL, 0, NULL, NULL}}; - -/* not returned: CAPSLOCKKEY, UNKNOWNKEY, COMMANDKEY, GRLESSKEY */ -EnumPropertyItem event_type_items[] = { - {AKEY, "A", 0, "A", ""}, - {BKEY, "B", 0, "B", ""}, - {CKEY, "C", 0, "C", ""}, - {DKEY, "D", 0, "D", ""}, - {EKEY, "E", 0, "E", ""}, - {FKEY, "F", 0, "F", ""}, - {GKEY, "G", 0, "G", ""}, - {HKEY, "H", 0, "H", ""}, - {IKEY, "I", 0, "I", ""}, - {JKEY, "J", 0, "J", ""}, - {KKEY, "K", 0, "K", ""}, - {LKEY, "L", 0, "L", ""}, - {MKEY, "M", 0, "M", ""}, - {NKEY, "N", 0, "N", ""}, - {OKEY, "O", 0, "O", ""}, - {PKEY, "P", 0, "P", ""}, - {QKEY, "Q", 0, "Q", ""}, - {RKEY, "R", 0, "R", ""}, - {SKEY, "S", 0, "S", ""}, - {TKEY, "T", 0, "T", ""}, - {UKEY, "U", 0, "U", ""}, - {VKEY, "V", 0, "V", ""}, - {WKEY, "W", 0, "W", ""}, - {XKEY, "X", 0, "X", ""}, - {YKEY, "Y", 0, "Y", ""}, - {ZKEY, "Z", 0, "Z", ""}, - - {ZEROKEY, "ZERO", 0, "Zero Key", ""}, - {ONEKEY, "ONE", 0, "One Key", ""}, - {TWOKEY, "TWO", 0, "Two Key", ""}, - {THREEKEY, "THREE", 0, "Three Key", ""}, - {FOURKEY, "FOUR", 0, "Four Key", ""}, - {FIVEKEY, "FIVE", 0, "Five Key", ""}, - {SIXKEY, "SIX", 0, "Six Key", ""}, - {SEVENKEY, "SEVEN", 0, "Seven Key", ""}, - {EIGHTKEY, "EIGHT", 0, "Eight Key", ""}, - {NINEKEY, "NINE", 0, "Nine Key", ""}, - - {LEFTCTRLKEY, "LEFT_CTRL", 0, "Left Ctrl", ""}, - {LEFTALTKEY, "LEFT_ALT", 0, "Left Alt", ""}, - {RIGHTALTKEY, "RIGHT_ALT", 0, "Right Alt", ""}, - {RIGHTCTRLKEY, "RIGHT_CTRL", 0, "Rightctrl", ""}, - {RIGHTSHIFTKEY, "RIGHT_SHIFT", 0, "Rightshift", ""}, - {LEFTSHIFTKEY, "LEFT_SHIFT", 0, "Leftshift", ""}, - - {ESCKEY, "ESC", 0, "Esc", ""}, - {TABKEY, "TAB", 0, "Tab", ""}, - {RETKEY, "RET", 0, "Return", ""}, - {SPACEKEY, "SPACE", 0, "Spacebar", ""}, - {LINEFEEDKEY, "LINE_FEED", 0, "Line Feed", ""}, - {BACKSPACEKEY, "BACK_SPACE", 0, "Back Space", ""}, - {DELKEY, "DEL", 0, "Delete", ""}, - {SEMICOLONKEY, "SEMI_COLON", 0, "Semicolon", ""}, - {PERIODKEY, "PERIOD", 0, "Period", ""}, - {COMMAKEY, "COMMA", 0, "Comma", ""}, - {QUOTEKEY, "QUOTE", 0, "Quote", ""}, - {ACCENTGRAVEKEY, "ACCENT_GRAVE", 0, "Accentgrave", ""}, - {MINUSKEY, "MINUS", 0, "Minus", ""}, - {SLASHKEY, "SLASH", 0, "Slash", ""}, - {BACKSLASHKEY, "BACK_SLASH", 0, "Backslash", ""}, - {EQUALKEY, "EQUAL", 0, "Equal", ""}, - {LEFTBRACKETKEY, "LEFT_BRACKET", 0, "Leftbracket", ""}, - {RIGHTBRACKETKEY, "RIGHT_BRACKET", 0, "Rightbracket", ""}, - {LEFTARROWKEY, "LEFT_ARROW", 0, "Left Arrow", ""}, - {DOWNARROWKEY, "DOWN_ARROW", 0, "Down Arrow", ""}, - {RIGHTARROWKEY, "RIGHT_ARROW", 0, "Right Arrow", ""}, - {UPARROWKEY, "UP_ARROW", 0, "Up Arrow", ""}, - {PAD2, "NUMPAD_2", 0, "Numpad 2", ""}, - {PAD4, "NUMPAD_4", 0, "Numpad 4", ""}, - {PAD6, "NUMPAD_6", 0, "Numpad 6", ""}, - {PAD8, "NUMPAD_8", 0, "Numpad 8", ""}, - {PAD1, "NUMPAD_1", 0, "Numpad 1", ""}, - {PAD3, "NUMPAD_3", 0, "Numpad 3", ""}, - {PAD5, "NUMPAD_5", 0, "Numpad 5", ""}, - {PAD7, "NUMPAD_7", 0, "Numpad 7", ""}, - {PAD9, "NUMPAD_9", 0, "Numpad 9", ""}, - {PADPERIOD, "NUMPAD_PERIOD", 0, "Numpad .", ""}, - {PADSLASHKEY, "NUMPAD_SLASH", 0, "Numpad /", ""}, - {PADASTERKEY, "NUMPAD_ASTERIX", 0, "Numpad *", ""}, - {PAD0, "NUMPAD_0", 0, "Numpad 0", ""}, - {PADMINUS, "NUMPAD_MINUS", 0, "Numpad -", ""}, - {PADENTER, "NUMPAD_ENTER", 0, "Numpad Enter", ""}, - {PADPLUSKEY, "NUMPAD_PLUS", 0, "Numpad +", ""}, - {F1KEY, "F1", 0, "F1", ""}, - {F2KEY, "F2", 0, "F2", ""}, - {F3KEY, "F3", 0, "F3", ""}, - {F4KEY, "F4", 0, "F4", ""}, - {F5KEY, "F5", 0, "F5", ""}, - {F6KEY, "F6", 0, "F6", ""}, - {F7KEY, "F7", 0, "F7", ""}, - {F8KEY, "F8", 0, "F8", ""}, - {F9KEY, "F9", 0, "F9", ""}, - {F10KEY, "F10", 0, "F10", ""}, - {F11KEY, "F11", 0, "F11", ""}, - {F12KEY, "F12", 0, "F12", ""}, - {PAUSEKEY, "PAUSE", 0, "Pause", ""}, - {INSERTKEY, "INSERT", 0, "Insert", ""}, - {HOMEKEY, "HOME", 0, "Home", ""}, - {PAGEUPKEY, "PAGE_UP", 0, "Page Up", ""}, - {PAGEDOWNKEY, "PAGE_DOWN", 0, "Page Down", ""}, - {ENDKEY, "END", 0, "End", ""}, - {0, NULL, 0, NULL, NULL}}; #ifdef RNA_RUNTIME @@ -201,20 +87,6 @@ static PointerRNA rna_Operator_properties_get(PointerRNA *ptr) return rna_pointer_inherit_refine(ptr, &RNA_OperatorProperties, op->properties); } - -static void rna_Event_ascii_get(PointerRNA *ptr, char *value) -{ - wmEvent *event= (wmEvent*)ptr->id.data; - value[0]= event->ascii; - value[1]= '\0'; -} - -static int rna_Event_ascii_length(PointerRNA *ptr) -{ - wmEvent *event= (wmEvent*)ptr->id.data; - return (event->ascii)? 1 : 0; -} - #else static void rna_def_operator(BlenderRNA *brna) @@ -274,80 +146,7 @@ static void rna_def_operator_filelist_element(BlenderRNA *brna) RNA_def_property_flag(prop, PROP_IDPROPERTY); RNA_def_property_ui_text(prop, "Name", "the name of a file or directory within a file list"); } - -static void rna_def_event(BlenderRNA *brna) -{ - StructRNA *srna; - PropertyRNA *prop; - - srna= RNA_def_struct(brna, "Event", NULL); - RNA_def_struct_ui_text(srna, "Event", "Window Manager Event"); - RNA_def_struct_sdna(srna, "wmEvent"); - - /* strings */ - prop= RNA_def_property(srna, "ascii", PROP_STRING, PROP_NONE); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_string_funcs(prop, "rna_Event_ascii_get", "rna_Event_ascii_length", NULL); - RNA_def_property_ui_text(prop, "ASCII", "Single ASCII character for this event."); - - - /* enums */ - prop= RNA_def_property(srna, "value", PROP_ENUM, PROP_NONE); - RNA_def_property_enum_sdna(prop, NULL, "val"); - RNA_def_property_enum_items(prop, event_value_items); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Value", "The type of event, only applies to some."); - - prop= RNA_def_property(srna, "type", PROP_ENUM, PROP_NONE); - RNA_def_property_enum_sdna(prop, NULL, "type"); - RNA_def_property_enum_items(prop, event_type_items); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Type", ""); - - - /* mouse */ - prop= RNA_def_property(srna, "mouse_x", PROP_INT, PROP_NONE); - RNA_def_property_int_sdna(prop, NULL, "x"); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Mouse X Position", "The window relative vertical location of the mouse."); - - prop= RNA_def_property(srna, "mouse_y", PROP_INT, PROP_NONE); - RNA_def_property_int_sdna(prop, NULL, "y"); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Mouse Y Position", "The window relative horizontal location of the mouse."); - - prop= RNA_def_property(srna, "mouse_prev_x", PROP_INT, PROP_NONE); - RNA_def_property_int_sdna(prop, NULL, "prevx"); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Mouse Previous X Position", "The window relative vertical location of the mouse."); - - prop= RNA_def_property(srna, "mouse_prev_y", PROP_INT, PROP_NONE); - RNA_def_property_int_sdna(prop, NULL, "prevy"); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Mouse Previous Y Position", "The window relative horizontal location of the mouse."); - - /* modifiers */ - prop= RNA_def_property(srna, "shift", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "shift", 1); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Shift", "True when the shift key is held."); - - prop= RNA_def_property(srna, "ctrl", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "ctrl", 1); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Ctrl", "True when the shift key is held."); - - prop= RNA_def_property(srna, "alt", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "alt", 1); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "Alt", "True when the shift key is held."); - - prop= RNA_def_property(srna, "oskey", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "oskey", 1); - RNA_def_property_clear_flag(prop, PROP_EDITABLE); - RNA_def_property_ui_text(prop, "OS Key", "True when the shift key is held."); -} static void rna_def_windowmanager(BlenderRNA *brna) { @@ -370,7 +169,6 @@ void RNA_def_wm(BlenderRNA *brna) rna_def_operator(brna); rna_def_operator_utils(brna); rna_def_operator_filelist_element(brna); - rna_def_event(brna); rna_def_windowmanager(brna); } diff --git a/source/blender/makesrna/intern/rna_wm_api.c b/source/blender/makesrna/intern/rna_wm_api.c index fd34d7c4d70..87a94993a42 100644 --- a/source/blender/makesrna/intern/rna_wm_api.c +++ b/source/blender/makesrna/intern/rna_wm_api.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_wm_api.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/makesrna/intern/rna_world.c b/source/blender/makesrna/intern/rna_world.c index f5eb81e3cea..e313f01c194 100644 --- a/source/blender/makesrna/intern/rna_world.c +++ b/source/blender/makesrna/intern/rna_world.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: rna_world.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -337,7 +337,7 @@ void RNA_def_world(BlenderRNA *brna) static EnumPropertyItem physics_engine_items[] = { {WOPHY_NONE, "NONE", 0, "None", ""}, //{WOPHY_ENJI, "ENJI", 0, "Enji", ""}, - //{WOPHY_SUMO, "SUMO", 0, "Sumo (Deprecated)", ""}, + {WOPHY_SUMO, "SUMO", 0, "Sumo (Deprecated)", ""}, //{WOPHY_DYNAMO, "DYNAMO", 0, "Dynamo", ""}, //{WOPHY_ODE, "ODE", 0, "ODE", ""}, {WOPHY_BULLET, "BULLET", 0, "Bullet", ""}, diff --git a/source/blender/python/BPY_extern.h b/source/blender/python/BPY_extern.h index d141a585378..855fdde50c5 100644 --- a/source/blender/python/BPY_extern.h +++ b/source/blender/python/BPY_extern.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: BPY_extern.h 12334 2007-10-21 23:00:29Z aligorith $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -50,8 +50,6 @@ struct bConstraintTarget; /* DNA_constraint_types.h*/ struct Script; /* DNA_screen_types.h */ struct BPyMenu; struct bContext; -struct ReportList; - #ifdef __cplusplus extern "C" { #endif diff --git a/source/blender/python/BPY_menus.c b/source/blender/python/BPY_menus.c new file mode 100644 index 00000000000..b67f1e717da --- /dev/null +++ b/source/blender/python/BPY_menus.c @@ -0,0 +1,1118 @@ +/* + * $Id: BPY_menus.c 12932 2007-12-17 20:21:06Z theeth $ + * + * ***** BEGIN GPL/BL DUAL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. The Blender + * Foundation also sells licenses for use in proprietary software under + * the Blender License. See http://www.blender.org/BL/ for information + * about this. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * This is a new part of Blender. + * + * Contributor(s): Willian P. Germano, Michael Reimpell + * + * ***** END GPL/BL DUAL LICENSE BLOCK ***** +*/ + +/* + *This is the main file responsible for having bpython scripts accessible + * from Blender menus. To know more, please start with its header file. + */ + +#include "BPY_menus.h" + +#include <Python.h> +#ifndef WIN32 + #include <dirent.h> +#else + #include "BLI_winstuff.h" +#endif +#include "BKE_global.h" +#include "BKE_utildefines.h" +#include "BLI_blenlib.h" +#include "MEM_guardedalloc.h" +#include "DNA_userdef_types.h" /* for U.pythondir */ +#include "api2_2x/EXPP_interface.h" /* for bpy_gethome() */ + +#define BPYMENU_DATAFILE "Bpymenus" +#define MAX_DIR_DEPTH 4 /* max depth for traversing scripts dirs */ +#define MAX_DIR_NUMBER 30 /* max number of dirs in scripts dirs trees */ + +static int DEBUG; +static int Dir_Depth; +static int Dirs_Number; + +/* BPyMenuTable holds all registered pymenus, as linked lists for each menu + * where they can appear (see PYMENUHOOKS enum in BPY_menus.h). +*/ +BPyMenu *BPyMenuTable[PYMENU_TOTAL]; + +static int bpymenu_group_atoi( char *str ) +{ + if( !strcmp( str, "Export" ) ) + return PYMENU_EXPORT; + else if( !strcmp( str, "Import" ) ) + return PYMENU_IMPORT; + else if( !strcmp( str, "Help" ) ) + return PYMENU_HELP; + else if( !strcmp( str, "HelpWebsites" ) ) + return PYMENU_HELPWEBSITES; + else if( !strcmp( str, "HelpSystem" ) ) + return PYMENU_HELPSYSTEM; + else if( !strcmp( str, "Render" ) ) + return PYMENU_RENDER; + else if( !strcmp( str, "System" ) ) + return PYMENU_SYSTEM; + else if( !strcmp( str, "Object" ) ) + return PYMENU_OBJECT; + else if( !strcmp( str, "Mesh" ) ) + return PYMENU_MESH; + else if( !strncmp( str, "Theme", 5 ) ) + return PYMENU_THEMES; + else if( !strcmp( str, "Add" ) ) + return PYMENU_ADD; + else if( !strcmp( str, "Wizards" ) ) + return PYMENU_WIZARDS; + else if( !strcmp( str, "Animation" ) ) + return PYMENU_ANIMATION; + else if( !strcmp( str, "Materials" ) ) + return PYMENU_MATERIALS; + else if( !strcmp( str, "UV" ) ) + return PYMENU_UV; + else if( !strcmp( str, "Image" ) ) + return PYMENU_IMAGE; + else if( !strcmp( str, "FaceSelect" ) ) + return PYMENU_FACESELECT; + else if( !strcmp( str, "WeightPaint" ) ) + return PYMENU_WEIGHTPAINT; + else if( !strcmp( str, "VertexPaint" ) ) + return PYMENU_VERTEXPAINT; + else if( !strcmp( str, "UVCalculation" ) ) + return PYMENU_UVCALCULATION; + else if( !strcmp( str, "Armature" ) ) + return PYMENU_ARMATURE; + else if( !strcmp( str, "ScriptTemplate" ) ) + return PYMENU_SCRIPTTEMPLATE; + else if( !strcmp( str, "MeshFaceKey" ) ) + return PYMENU_MESHFACEKEY; + else if( !strcmp( str, "AddMesh" ) ) + return PYMENU_ADDMESH; + /* "Misc" or an inexistent group name: use misc */ + else + return PYMENU_MISC; +} + +char *BPyMenu_group_itoa( short menugroup ) +{ + switch ( menugroup ) { + case PYMENU_EXPORT: + return "Export"; + break; + case PYMENU_IMPORT: + return "Import"; + break; + case PYMENU_ADD: + return "Add"; + break; + case PYMENU_HELP: + return "Help"; + break; + case PYMENU_HELPWEBSITES: + return "HelpWebsites"; + break; + case PYMENU_HELPSYSTEM: + return "HelpSystem"; + break; + case PYMENU_RENDER: + return "Render"; + break; + case PYMENU_SYSTEM: + return "System"; + break; + case PYMENU_OBJECT: + return "Object"; + break; + case PYMENU_MESH: + return "Mesh"; + break; + case PYMENU_THEMES: + return "Themes"; + break; + case PYMENU_WIZARDS: + return "Wizards"; + break; + case PYMENU_ANIMATION: + return "Animation"; + break; + case PYMENU_MATERIALS: + return "Materials"; + break; + case PYMENU_UV: + return "UV"; + break; + case PYMENU_IMAGE: + return "Image"; + break; + case PYMENU_FACESELECT: + return "FaceSelect"; + break; + case PYMENU_WEIGHTPAINT: + return "WeightPaint"; + break; + case PYMENU_VERTEXPAINT: + return "VertexPaint"; + break; + case PYMENU_UVCALCULATION: + return "UVCalculation"; + break; + case PYMENU_ARMATURE: + return "Armature"; + break; + case PYMENU_SCRIPTTEMPLATE: + return "ScriptTemplate"; + break; + case PYMENU_MESHFACEKEY: + return "MeshFaceKey"; + break; + case PYMENU_ADDMESH: + return "AddMesh"; + break; + case PYMENU_MISC: + return "Misc"; + break; + } + return NULL; +} + +/* BPyMenu_CreatePupmenuStr: + * build and return a meaninful string to be used by pupmenu(). The + * string is made of a bpymenu name as title and its submenus as possible + * choices for the user. +*/ +char *BPyMenu_CreatePupmenuStr( BPyMenu * pym, short menugroup ) +{ + BPySubMenu *pysm = pym->submenus; + char str[1024], str2[100]; + int i = 0, rlen; + + if( !pym || !pysm ) + return NULL; + + str[0] = '\0'; + + PyOS_snprintf( str2, sizeof( str2 ), "%s: %s%%t", + BPyMenu_group_itoa( menugroup ), pym->name ); + strcat( str, str2 ); + + while( pysm ) { + PyOS_snprintf( str2, sizeof( str2 ), "|%s%%x%d", pysm->name, + i ); + rlen = sizeof( str ) - strlen( str ); + strncat( str, str2, rlen ); + i++; + pysm = pysm->next; + } + + return BLI_strdup( str ); +} + +static void bpymenu_RemoveAllSubEntries( BPySubMenu * smenu ) +{ + BPySubMenu *tmp; + + while( smenu ) { + tmp = smenu->next; + if( smenu->name ) + MEM_freeN( smenu->name ); + if( smenu->arg ) + MEM_freeN( smenu->arg ); + MEM_freeN( smenu ); + smenu = tmp; + } + return; +} + +void BPyMenu_RemoveAllEntries( void ) +{ + BPyMenu *tmp, *pymenu; + int i; + + for( i = 0; i < PYMENU_TOTAL; i++ ) { + pymenu = BPyMenuTable[i]; + while( pymenu ) { + tmp = pymenu->next; + if( pymenu->name ) + MEM_freeN( pymenu->name ); + if( pymenu->filename ) + MEM_freeN( pymenu->filename ); + if( pymenu->tooltip ) + MEM_freeN( pymenu->tooltip ); + if( pymenu->submenus ) + bpymenu_RemoveAllSubEntries( pymenu-> + submenus ); + MEM_freeN( pymenu ); + pymenu = tmp; + } + BPyMenuTable[i] = NULL; + } + + Dirs_Number = 0; + Dir_Depth = 0; + + return; +} + +static BPyMenu *bpymenu_FindEntry( short group, char *name ) +{ + BPyMenu *pymenu; + + if( ( group < 0 ) || ( group >= PYMENU_TOTAL ) ) + return NULL; + + pymenu = BPyMenuTable[group]; + + while( pymenu ) { + if( !strcmp( pymenu->name, name ) ) + return pymenu; + pymenu = pymenu->next; + } + + return NULL; +} + +/* BPyMenu_GetEntry: + * given a group and a position, return the entry in that position from + * that group. +*/ +BPyMenu *BPyMenu_GetEntry( short group, short pos ) +{ + BPyMenu *pym = NULL; + + if( ( group < 0 ) || ( group >= PYMENU_TOTAL ) ) + return NULL; + + pym = BPyMenuTable[group]; + + while( pos-- ) { + if( pym ) + pym = pym->next; + else + break; + } + + return pym; /* found entry or NULL */ +} + +static void bpymenu_set_tooltip( BPyMenu * pymenu, char *tip ) +{ + if( !pymenu ) + return; + + if( pymenu->tooltip ) + MEM_freeN( pymenu->tooltip ); + pymenu->tooltip = BLI_strdup( tip ); + + return; +} + +/* bpymenu_AddEntry: + * try to find an existing pymenu entry with the given type and name; + * if found, update it with new info, otherwise create a new one and fill it. + */ +static BPyMenu *bpymenu_AddEntry( short group, short version, char *name, + char *fname, int is_userdir, char *tooltip ) +{ + BPyMenu *menu, *next = NULL, **iter; + int nameclash = 0; + + if( ( group < 0 ) || ( group >= PYMENU_TOTAL ) ) + return NULL; + if( !name || !fname ) + return NULL; + + menu = bpymenu_FindEntry( group, name ); /* already exists? */ + + /* if a menu with this name already exists in the same group: + * - if one script is in the default dir and the other in U.pythondir, + * accept and let the new one override the other. + * - otherwise, report the error and return NULL. */ + if( menu ) { + if( menu->dir < is_userdir ) { /* new one is in U.pythondir */ + nameclash = 1; + if( menu->name ) + MEM_freeN( menu->name ); + if( menu->filename ) + MEM_freeN( menu->filename ); + if( menu->tooltip ) + MEM_freeN( menu->tooltip ); + if( menu->submenus ) + bpymenu_RemoveAllSubEntries( menu->submenus ); + next = menu->next; + } else { /* they are in the same dir */ + if (DEBUG) { + fprintf(stderr, "\n\ +Warning: script %s's menu name is already in use.\n\ +Edit the script and change its \n\ +Name: '%s'\n\ +field, please.\n\ +Note: if you really want to have two scripts for the same menu with\n\ +the same name, keep one in the default dir and the other in\n\ +the user defined dir (only the later will be registered).\n", fname, name); + } + return NULL; + } + } else + menu = MEM_mallocN( sizeof( BPyMenu ), "pymenu" ); + + if( !menu ) + return NULL; + + menu->name = BLI_strdup( name ); + menu->version = version; + menu->filename = BLI_strdup( fname ); + menu->tooltip = NULL; + if( tooltip ) + menu->tooltip = BLI_strdup( tooltip ); + menu->dir = is_userdir; + menu->submenus = NULL; + menu->next = next; /* non-NULL if menu already existed */ + + if( nameclash ) + return menu; /* no need to place it, it's already at the list */ + else { /* insert the new entry in its correct position at the table */ + BPyMenu *prev = NULL; + char *s = NULL; + + iter = &BPyMenuTable[group]; + while( *iter ) { + s = ( *iter )->name; + if( s ) + if( strcmp( menu->name, s ) < 0 ) + break; /* sort by names */ + prev = *iter; + iter = &( ( *iter )->next ); + } + + if( *iter ) { /* prepend */ + menu->next = *iter; + if( prev ) + prev->next = menu; + else + BPyMenuTable[group] = menu; /* is first entry */ + } else + *iter = menu; /* append */ + } + + return menu; +} + +/* bpymenu_AddSubEntry: + * add a submenu to an existing python menu. + */ +static int bpymenu_AddSubEntry( BPyMenu * mentry, char *name, char *arg ) +{ + BPySubMenu *smenu, **iter; + + smenu = MEM_mallocN( sizeof( BPySubMenu ), "pysubmenu" ); + if( !smenu ) + return -1; + + smenu->name = BLI_strdup( name ); + smenu->arg = BLI_strdup( arg ); + smenu->next = NULL; + + if( !smenu->name || !smenu->arg ) + return -1; + + iter = &( mentry->submenus ); + while( *iter ) + iter = &( ( *iter )->next ); + + *iter = smenu; + + return 0; +} + +/* bpymenu_CreateFromFile: + * parse the bpymenus data file where Python menu data is stored; + * based on this data, create and fill the pymenu structs. + */ +static int bpymenu_CreateFromFile( void ) +{ + FILE *fp; + char line[255], w1[255], w2[255], tooltip[255], *tip; + char *homedir = NULL; + int parsing, version, is_userdir; + short group; + BPyMenu *pymenu = NULL; + + /* init global bpymenu table (it is a list of pointers to struct BPyMenus + * for each available cathegory: import, export, etc.) */ + for( group = 0; group < PYMENU_TOTAL; group++ ) + BPyMenuTable[group] = NULL; + + /* let's try to open the file with bpymenu data */ + homedir = bpy_gethome(0); + if (!homedir) { + if( DEBUG ) + fprintf(stderr, + "BPyMenus error: couldn't open config file Bpymenus: no home dir.\n"); + return -1; + } + + BLI_make_file_string( "/", line, homedir, BPYMENU_DATAFILE ); + + fp = fopen( line, "rb" ); + + if( !fp ) { + if( DEBUG ) + fprintf(stderr, "BPyMenus error: couldn't open config file %s.\n", line ); + return -1; + } + + fgets( line, 255, fp ); /* header */ + + /* check if the U.pythondir we saved at the file is different from the + * current one. If so, return to force updating from dirs */ + w1[0] = '\0'; + fscanf( fp, "# User defined scripts dir: %[^\n]\n", w1 ); + if( w1 ) { + char upythondir[FILE_MAXDIR]; + + BLI_strncpy(upythondir, U.pythondir, FILE_MAXDIR); + BLI_convertstringcode(upythondir, G.sce, 0); + if( strcmp( w1, upythondir ) != 0 ) + return -1; + w1[0] = '\0'; + } + + while( fgets( line, 255, fp ) ) { /* parsing file lines */ + + switch ( line[0] ) { /* check first char */ + case '#': /* comment */ + continue; + break; + case '\n': + continue; + break; + default: + parsing = sscanf( line, "%s {\n", w1 ); /* menu group */ + break; + } + + if( parsing == 1 ) { /* got menu group string */ + group = (short)bpymenu_group_atoi( w1 ); + if( group < 0 && DEBUG ) { /* invalid type */ + fprintf(stderr, + "BPyMenus error parsing config file: wrong group: %s,\n\ +will use 'Misc'.\n", w1 ); + } + } else + continue; + + for(;;) { + tip = NULL; /* optional tooltip */ + fgets( line, 255, fp ); + if( line[0] == '}' ) + break; + else if( line[0] == '\n' ) + continue; + else if( line[0] == '\'' ) { /* menu entry */ + parsing = + sscanf( line, + "'%[^']' %d %s %d '%[^']'\n", + w1, &version, w2, &is_userdir, + tooltip ); + + if( parsing <= 0 ) { /* invalid line, get rid of it */ + fgets( line, 255, fp ); + } else if( parsing == 5 ) + tip = tooltip; /* has tooltip */ + + pymenu = bpymenu_AddEntry( group, + ( short ) version, + w1, w2, is_userdir, + tip ); + if( !pymenu ) { + puts( "BPyMenus error: couldn't create bpymenu entry.\n" ); + fclose( fp ); + return -1; + } + } else if( line[0] == '|' && line[1] == '_' ) { /* menu sub-entry */ + if( !pymenu ) + continue; /* no menu yet, skip this line */ + sscanf( line, "|_%[^:]: %s\n", w1, w2 ); + bpymenu_AddSubEntry( pymenu, w1, w2 ); + } + } + } + + fclose( fp ); + return 0; +} + +/* bpymenu_WriteDataFile: + * writes the registered scripts info to the user's home dir, for faster + * access when the scripts dir hasn't changed. +*/ +static void bpymenu_WriteDataFile( void ) +{ + BPyMenu *pymenu; + BPySubMenu *smenu; + FILE *fp; + char fname[FILE_MAXDIR], *homedir; + int i; + + homedir = bpy_gethome(0); + + if (!homedir) { + if( DEBUG ) + fprintf(stderr, + "BPyMenus error: couldn't write Bpymenus file: no home dir.\n\n"); + return; + } + + BLI_make_file_string( "/", fname, homedir, BPYMENU_DATAFILE ); + + fp = fopen( fname, "w" ); + if( !fp ) { + if( DEBUG ) + fprintf(stderr, "BPyMenus error: couldn't write %s file.\n\n", + fname ); + return; + } + + fprintf( fp, + "# Blender: registered menu entries for bpython scripts\n" ); + + if (U.pythondir[0] != '\0' && + strcmp(U.pythondir, "/") != 0 && strcmp(U.pythondir, "//") != 0) + { + char upythondir[FILE_MAXDIR]; + + BLI_strncpy(upythondir, U.pythondir, FILE_MAXDIR); + BLI_convertstringcode(upythondir, G.sce, 0); + fprintf( fp, "# User defined scripts dir: %s\n", upythondir ); + } + + for( i = 0; i < PYMENU_TOTAL; i++ ) { + pymenu = BPyMenuTable[i]; + if( !pymenu ) + continue; + fprintf( fp, "\n%s {\n", BPyMenu_group_itoa( (short)i ) ); + while( pymenu ) { + fprintf( fp, "'%s' %d %s %d", pymenu->name, + pymenu->version, pymenu->filename, + pymenu->dir ); + if( pymenu->tooltip ) + fprintf( fp, " '%s'\n", pymenu->tooltip ); + else + fprintf( fp, "\n" ); + smenu = pymenu->submenus; + while( smenu ) { + fprintf( fp, "|_%s: %s\n", smenu->name, + smenu->arg ); + smenu = smenu->next; + } + pymenu = pymenu->next; + } + fprintf( fp, "}\n" ); + } + + fclose( fp ); + return; +} + +/* BPyMenu_PrintAllEntries: + * useful for debugging. + */ +void BPyMenu_PrintAllEntries( void ) +{ + BPyMenu *pymenu; + BPySubMenu *smenu; + int i; + + printf( "# Blender: registered menu entries for bpython scripts\n" ); + + for( i = 0; i < PYMENU_TOTAL; i++ ) { + pymenu = BPyMenuTable[i]; + printf( "\n%s {\n", BPyMenu_group_itoa( (short)i ) ); + while( pymenu ) { + printf( "'%s' %d %s %d", pymenu->name, pymenu->version, + pymenu->filename, pymenu->dir ); + if( pymenu->tooltip ) + printf( " '%s'\n", pymenu->tooltip ); + else + printf( "\n" ); + smenu = pymenu->submenus; + while( smenu ) { + printf( "|_%s: %s\n", smenu->name, + smenu->arg ); + smenu = smenu->next; + } + pymenu = pymenu->next; + } + printf( "}\n" ); + } +} + +/* bpymenu_ParseFile: + * recursively scans folders looking for scripts to register. + * + * This function scans the scripts directory looking for .py files with the + * right header and menu info, using that to fill the bpymenu structs. + * is_userdir defines if the script is in the default scripts dir or the + * user defined one (U.pythondir: is_userdir == 1). + * Speed is important. + * + * The first line of the script must be '#!BPY'. + * The header registration lines must appear between the first pair of + * '\"\"\"' and follow this order (the single-quotes are part of + * the format): + * + * # \"\"\"<br> + * # Name: 'script name for the menu' + * # Blender: <code>short int</code> (minimal Blender version) + * # Group: 'group name' (defines menu) + * # Submenu: 'submenu name' related_1word_arg + * # Tooltip: 'tooltip for the menu' + * # \"\"\" + * + * Notes: + * + * - Commenting out header lines with "#" is optional, but recommended. + * - There may be more than one submenu line, or none: + * submenus and the tooltip are optional; + * - The Blender version is the same number reported by + * Blender.Get('version') in BPython or G.version in C; + * - Line length must be less than 99. + */ +static int bpymenu_ParseFile(FILE *file, char *fname, int is_userdir) +{ + char line[100]; + char head[100]; + char middle[100]; + char tail[100]; + int matches; + int parser_state; + + char script_name[100]; + int script_version = 1; + int script_group; + + BPyMenu *scriptMenu = NULL; + + if (file != NULL) { + parser_state = 1; /* state of parser, 0 to terminate */ + + while ((parser_state != 0) && (fgets(line, 100, file) != NULL)) { + + switch (parser_state) { + + case 1: /* !BPY */ + if (strncmp(line, "#!BPY", 5) == 0) { + parser_state++; + } else { + parser_state = 0; + } + break; + + case 2: /* \"\"\" */ + if ((strstr(line, "\"\"\""))) { + parser_state++; + } + break; + + case 3: /* Name: 'script name for the menu' */ + matches = sscanf(line, "%[^']'%[^']'%c", head, script_name, tail); + if ((matches == 3) && (strstr(head, "Name:") != NULL)) { + parser_state++; + } else { + if (DEBUG) + fprintf(stderr, "BPyMenus error: Wrong 'Name' line: %s\n", fname); + parser_state = 0; + } + break; + + case 4: /* Blender: <short int> */ + matches = sscanf(line, "%[^1234567890]%i%c", head, &script_version, + tail); + if (matches == 3) { + parser_state++; + } else { + if (DEBUG) + fprintf(stderr,"BPyMenus error: Wrong 'Blender' line: %s\n",fname); + parser_state = 0; + } + break; + + case 5: /* Group: 'group name' */ + matches = sscanf(line, "%[^']'%[^']'%c", head, middle, tail); + if ((matches == 3) && (strstr(head, "Group:") != NULL)) { + script_group = bpymenu_group_atoi(middle); + if (script_group < 0) { + if (DEBUG) + fprintf(stderr, "BPyMenus error: Unknown group \"%s\": %s\n", + middle, fname); + parser_state = 0; + } + + else { /* register script */ + scriptMenu = bpymenu_AddEntry((short)script_group, + (short int)script_version, script_name, fname, is_userdir,NULL); + if (scriptMenu == NULL) { + if (DEBUG) + fprintf(stderr, + "BPyMenus error: Couldn't create entry for: %s\n", fname); + parser_state = 0; + } else { + parser_state++; + } + } + + } else { + if (DEBUG) + fprintf(stderr, "BPyMenus error: Wrong 'Group' line: %s\n",fname); + parser_state = 0; + } + break; + + case 6: /* optional elements */ + /* Submenu: 'submenu name' related_1word_arg */ + matches = sscanf(line, "%[^']'%[^']'%s\n", head, middle, tail); + if ((matches == 3) && (strstr(head, "Submenu:") != NULL)) { + bpymenu_AddSubEntry(scriptMenu, middle, tail); + } else { + /* Tooltip: 'tooltip for the menu */ + matches = sscanf(line, "%[^']'%[^']'%c", head, middle, tail); + if ((matches == 3) && ((strstr(head, "Tooltip:") != NULL) || + (strstr(head, "Tip:") != NULL))) { + bpymenu_set_tooltip(scriptMenu, middle); + } + parser_state = 0; + } + break; + + default: + parser_state = 0; + break; + } + } + } + + else { /* shouldn't happen, it's checked in bpymenus_ParseDir */ + if (DEBUG) + fprintf(stderr, "BPyMenus error: Couldn't open %s.\n", fname); + return -1; + } + + return 0; +} + +/* bpymenu_ParseDir: + * recursively scans folders looking for scripts to register. + * + * This function scans the scripts directory looking for .py files with the + * right header and menu info. + * - is_userdir defines if the script is in the default scripts dir or the + * user defined one (U.pythondir: is_userdir == 1); + * - parentdir is the parent dir name to store as part of the script filename, + * if we're down a subdir. + * Speed is important. + */ +static int bpymenu_ParseDir(char *dirname, char *parentdir, int is_userdir ) +{ + DIR *dir; + FILE *file = NULL; + struct dirent *de; + struct stat status; + char *file_extension; + char path[FILE_MAX]; + char subdir[FILE_MAX]; + char *s = NULL; + + dir = opendir(dirname); + + if (dir != NULL) { + while ((de = readdir(dir)) != NULL) { + + /* skip files and dirs starting with '.' or 'bpy' */ + if ((de->d_name[0] == '.') || !strncmp(de->d_name, "bpy", 3)) { + continue; + } + + BLI_make_file_string("/", path, dirname, de->d_name); + + if (stat(path, &status) != 0) { + if (DEBUG) + fprintf(stderr, "stat %s failed: %s\n", path, strerror(errno)); + } + + if (S_ISREG(status.st_mode)) { /* is file */ + + file_extension = strstr(de->d_name, ".py"); + + if (file_extension && *(file_extension + 3) == '\0') { + file = fopen(path, "rb"); + + if (file) { + s = de->d_name; + if (parentdir) { + /* Join parentdir and de->d_name */ + BLI_join_dirfile(subdir, parentdir, de->d_name); + + s = subdir; + } + bpymenu_ParseFile(file, s, is_userdir); + fclose(file); + } + + else { + if (DEBUG) + fprintf(stderr, "BPyMenus error: Couldn't open %s.\n", path); + } + } + } + + else if (S_ISDIR(status.st_mode)) { /* is subdir */ + Dirs_Number++; + Dir_Depth++; + if (Dirs_Number > MAX_DIR_NUMBER) { + if (DEBUG) { + fprintf(stderr, "BPyMenus error: too many subdirs.\n"); + } + closedir(dir); + return -1; + } + else if (Dir_Depth > MAX_DIR_DEPTH) { + if (DEBUG) + fprintf(stderr, + "BPyMenus error: max depth reached traversing dir tree.\n"); + closedir(dir); + return -1; + } + s = de->d_name; + if (parentdir) { + /* Join parentdir and de->d_name */ + BLI_join_dirfile(subdir, parentdir, de->d_name); + s = subdir; + } + if (bpymenu_ParseDir(path, s, is_userdir) == -1) { + closedir(dir); + return -1; + } + Dir_Depth--; + } + + } + closedir(dir); + } + + else { /* open directory stream failed */ + if (DEBUG) + fprintf(stderr, "opendir %s failed: %s\n", dirname, strerror(errno)); + return -1; + } + + return 0; +} + +static int bpymenu_GetStatMTime( char *name, int is_file, time_t * mtime ) +{ + struct stat st; + int result; + + result = stat( name, &st ); + + if( result == -1 ) + return -1; + + if( is_file ) { + if( !S_ISREG( st.st_mode ) ) + return -2; + } else if( !S_ISDIR( st.st_mode ) ) + return -2; + + *mtime = st.st_mtime; + + return 0; +} + +/* BPyMenu_Init: + * import the bpython menus data to Blender, either from: + * - the BPYMENU_DATAFILE file (?/.blender/Bpymenus) or + * - the scripts dir(s), case newer than the datafile (then update the file). + * then fill the bpymenu table with this data. + * if param usedir != 0, then the data is recreated from the dir(s) anyway. +*/ +int BPyMenu_Init( int usedir ) +{ + char fname[FILE_MAXDIR]; + char dirname[FILE_MAXDIR]; + char upythondir[FILE_MAXDIR]; + char *upydir = U.pythondir, *sdir = NULL; + time_t time_dir1 = 0, time_dir2 = 0, time_file = 0; + int stat_dir1 = 0, stat_dir2 = 0, stat_file = 0; + int i; + + DEBUG = G.f & G_DEBUG; /* is Blender in debug mode (started with -d) ? */ + + /* init global bpymenu table (it is a list of pointers to struct BPyMenus + * for each available group: import, export, etc.) */ + for( i = 0; i < PYMENU_TOTAL; i++ ) + BPyMenuTable[i] = NULL; + + if( DEBUG ) + fprintf(stdout, "\nRegistering scripts in Blender menus ...\n\n" ); + + if( U.pythondir[0] == '\0') { + upydir = NULL; + } + else if (strcmp(U.pythondir, "/") == 0 || strcmp(U.pythondir, "//") == 0) { + /* these are not accepted to prevent possible slight slowdowns on startup; + * they should not be used as user defined scripts dir, anyway, also from + * speed considerations, since they'd not be dedicated scripts dirs */ + if (DEBUG) fprintf(stderr, + "BPyMenus: invalid user defined Python scripts dir: \"/\" or \"//\".\n"); + upydir = NULL; + } + else { + BLI_strncpy(upythondir, upydir, FILE_MAXDIR); + BLI_convertstringcode(upythondir, G.sce, 0); + } + + sdir = bpy_gethome(1); + + if (sdir) { + BLI_strncpy(dirname, sdir, FILE_MAXDIR); + stat_dir1 = bpymenu_GetStatMTime( dirname, 0, &time_dir1 ); + + if( stat_dir1 < 0 ) { + time_dir1 = 0; + if( DEBUG ) { + fprintf(stderr, + "\nDefault scripts dir: %s:\n%s\n", dirname, strerror(errno)); + if( upydir ) + fprintf(stdout, + "Getting scripts menu data from user defined dir: %s.\n", + upythondir ); + } + } + } + else stat_dir1 = -1; + + if( upydir ) { + stat_dir2 = bpymenu_GetStatMTime( upythondir, 0, &time_dir2 ); + + if( stat_dir2 < 0 ) { + time_dir2 = 0; + upydir = NULL; + if( DEBUG ) + fprintf(stderr, "\nUser defined scripts dir: %s:\n%s.\n", + upythondir, strerror( errno ) ); + if( stat_dir1 < 0 ) { + if( DEBUG ) + fprintf(stderr, "\ +To have scripts in menus, please add them to the default scripts dir:\n\ +%s\n\ +and / or go to 'Info window -> File Paths tab' and set a valid path for\n\ +the user defined Python scripts dir.\n", dirname ); + return -1; + } + } + } + else stat_dir2 = -1; + + if( ( stat_dir1 < 0 ) && ( stat_dir2 < 0 ) ) { + if( DEBUG ) { + fprintf(stderr, "\nCannot register scripts in menus, no scripts dir" + " available.\nExpected default dir at: %s \n", dirname ); + } + return -1; + } + + if (usedir) stat_file = -1; + else { /* if we're not forced to use the dir */ + char *homedir = bpy_gethome(0); + + if (homedir) { + BLI_make_file_string( "/", fname, homedir, BPYMENU_DATAFILE ); + stat_file = bpymenu_GetStatMTime( fname, 1, &time_file ); + if( stat_file < 0 ) + time_file = 0; + + /* comparing dates */ + + if((stat_file == 0) + && (time_file > time_dir1) && (time_file > time_dir2)) + { /* file is newer */ + stat_file = bpymenu_CreateFromFile( ); /* -1 if an error occurred */ + if( !stat_file && DEBUG ) + fprintf(stdout, + "Getting menu data for scripts from file:\n%s\n\n", fname ); + } + else stat_file = -1; + } + else stat_file = -1; /* -1 to use dirs: didn't use file or it was corrupted */ + } + + if( stat_file == -1 ) { /* use dirs */ + if( DEBUG ) { + fprintf(stdout, + "Getting menu data for scripts from dir(s):\ndefault: %s\n", dirname ); + if( upydir ) + fprintf(stdout, "user defined: %s\n", upythondir ); + fprintf(stdout, "\n"); + } + if( stat_dir1 == 0 ) { + i = bpymenu_ParseDir( dirname, NULL, 0 ); + if (i == -1 && DEBUG) + fprintf(stderr, "Default scripts dir does not seem valid.\n\n"); + } + if( stat_dir2 == 0 ) { + BLI_strncpy(dirname, U.pythondir, FILE_MAXDIR); + BLI_convertstringcode(dirname, G.sce, 0); + i = bpymenu_ParseDir( dirname, NULL, 1 ); + if (i == -1 && DEBUG) + fprintf(stderr, "User defined scripts dir does not seem valid.\n\n"); + } + + /* check if we got any data */ + for( i = 0; i < PYMENU_TOTAL; i++ ) + if( BPyMenuTable[i] ) + break; + + /* if we got, recreate the file */ + if( i < PYMENU_TOTAL ) + bpymenu_WriteDataFile( ); + else if( DEBUG ) { + fprintf(stderr, "\n\ +Warning: Registering scripts in menus -- no info found.\n\ +Either your scripts dirs have no .py scripts or the scripts\n\ +don't have a header with registration data.\n\ +Default scripts dir is:\n\ +%s\n", dirname ); + if( upydir ) + fprintf(stderr, "User defined scripts dir is: %s\n", + upythondir ); + } + } + + return 0; +} diff --git a/source/blender/python/BPY_menus.h b/source/blender/python/BPY_menus.h new file mode 100644 index 00000000000..6cdea608b10 --- /dev/null +++ b/source/blender/python/BPY_menus.h @@ -0,0 +1,128 @@ +/* + * $Id: BPY_menus.h 12931 2007-12-17 18:20:48Z theeth $ + * + * ***** BEGIN GPL/BL DUAL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. The Blender + * Foundation also sells licenses for use in proprietary software under + * the Blender License. See http://www.blender.org/BL/ for information + * about this. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * This is a new part of Blender. + * + * Contributor(s): Willian P. Germano, Matt Ebb + * + * ***** END GPL/BL DUAL LICENSE BLOCK ***** +*/ + +#ifndef BPY_MENUS_H +#define BPY_MENUS_H + +/* This header exposes BPyMenu related public declarations. The implementation + * adds 'dynamic' menus to Blender, letting scripts register themselves in any + * of a few pre-defined (trivial to upgrade) places in menus. These places or + * slots are called groups here (Import, Export, etc). This is how it works: + * - scripts at dirs user pref U.pythondir and .blender/scripts/ are scanned + * for registration info. + * - this data is also saved to a Bpymenus file at the user's .blender/ dir and + * only re-created when the scripts folder gets modified. + * - on start-up Blender uses this info to fill a table, which is used to + * create the menu entries when they are needed (see header_info.c or + * header_script.c, under source/blender/src/, for examples). +*/ + +/* These two structs hold py menu/submenu info. + * BPyMenu holds a script's name (as should appear in the menu) and filename, + * plus an optional list of submenus. Each submenu is related to a string + * (arg) that the script can get from the __script__ pydict, to know which + * submenu was chosen. */ + +typedef struct BPySubMenu { + char *name; + char *arg; + struct BPySubMenu *next; +} BPySubMenu; + +typedef struct BPyMenu { + char *name; + char *filename; + char *tooltip; + short version; /* Blender version */ + int dir; /* 0: default, 1: U.pythondir */ + struct BPySubMenu *submenus; + struct BPyMenu *next; +} BPyMenu; + +/* Scripts can be added to only a few pre-defined places in menus, like + * File->Import, File->Export, etc. (for speed and better control). + * To make a new menu 'slot' available for scripts: + * - add an entry to the enum below, before PYMENU_TOTAL, of course; + * - update the bpymenu_group_atoi() and BPyMenu_group_itoa() functions in + * BPY_menus.c; + * - add the necessary code to the header_***.c file in + * source/blender/src/, like done in header_info.c for import/export; +*/ +typedef enum { + PYMENU_ADD,/* creates new objects */ + PYMENU_ANIMATION, + PYMENU_EXPORT, + PYMENU_IMPORT, + PYMENU_MATERIALS, + PYMENU_MESH, + PYMENU_MISC, + PYMENU_OBJECT, + PYMENU_RENDER,/* exporters to external renderers */ + PYMENU_SYSTEM, + PYMENU_THEMES, + PYMENU_UV,/* UV editing tools, to go in UV/Image editor space, 'UV' menu */ + PYMENU_IMAGE,/* Image editing tools, to go in UV/Image editor space, 'Image' menu */ + PYMENU_WIZARDS,/* complex 'app' scripts */ + + /* entries put after Wizards don't appear at the Scripts win->Scripts menu; + * see define right below */ + + PYMENU_FACESELECT, + PYMENU_WEIGHTPAINT, + PYMENU_VERTEXPAINT, + PYMENU_UVCALCULATION, + PYMENU_ARMATURE, + PYMENU_SCRIPTTEMPLATE, + PYMENU_HELP,/*Main Help menu items - prob best to leave for 'official' ones*/ + PYMENU_HELPSYSTEM,/* Resources, troubleshooting, system tools */ + PYMENU_HELPWEBSITES,/* Help -> Websites submenu */ + PYMENU_MESHFACEKEY, /* face key in mesh editmode */ + PYMENU_ADDMESH, /* adds mesh */ + PYMENU_TOTAL +} PYMENUHOOKS; + +#define PYMENU_SCRIPTS_MENU_TOTAL (PYMENU_WIZARDS + 1) + +/* BPyMenuTable holds all registered pymenus, as linked lists for each menu + * where they can appear (see PYMENUHOOKS enum above). +*/ +extern BPyMenu *BPyMenuTable[]; /* defined in BPY_menus.c */ + +/* public functions: */ +int BPyMenu_Init( int usedir ); +void BPyMenu_RemoveAllEntries( void ); +void BPyMenu_PrintAllEntries( void ); +char *BPyMenu_CreatePupmenuStr( BPyMenu * pym, short group ); +char *BPyMenu_group_itoa( short group ); +struct BPyMenu *BPyMenu_GetEntry( short group, short pos ); + +#endif /* BPY_MENUS_H */ diff --git a/source/blender/python/Makefile b/source/blender/python/Makefile index 8e2a04b8449..0c4b9ab6578 100644 --- a/source/blender/python/Makefile +++ b/source/blender/python/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 14444 2008-04-16 22:40:48Z hos $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/python/generic/BGL.c b/source/blender/python/generic/BGL.c index de82781cf3a..f1a72270ea1 100644 --- a/source/blender/python/generic/BGL.c +++ b/source/blender/python/generic/BGL.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: BGL.c 20922 2009-06-16 07:16:51Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -83,13 +83,8 @@ static PyObject *Buffer_getattr( PyObject * self, char *name ); static PyObject *Buffer_repr( PyObject * self ); PyTypeObject buffer_Type = { -#if (PY_VERSION_HEX >= 0x02060000) - PyVarObject_HEAD_INIT(NULL, 0) -#else - /* python 2.5 and below */ - PyObject_HEAD_INIT( NULL ) /* required py macro */ - 0, /* ob_size */ -#endif + PyObject_HEAD_INIT( NULL ) /* required python macro */ + 0, /*ob_size */ "buffer", /*tp_name */ sizeof( Buffer ), /*tp_basicsize */ 0, /*tp_itemsize */ @@ -1092,7 +1087,7 @@ static struct PyMethodDef BGL_methods[] = { #if (PY_VERSION_HEX >= 0x03000000) static struct PyModuleDef BGL_module_def = { - PyModuleDef_HEAD_INIT, + {}, /* m_base */ "BGL", /* m_name */ 0, /* m_doc */ 0, /* m_size */ diff --git a/source/blender/python/generic/BGL.h b/source/blender/python/generic/BGL.h index 938c916bcea..e2d1b0bb495 100755 --- a/source/blender/python/generic/BGL.h +++ b/source/blender/python/generic/BGL.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: BGL.h 19717 2009-04-14 17:19:09Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/python/generic/Geometry.c b/source/blender/python/generic/Geometry.c index 8a748241570..d1e8b471f75 100644 --- a/source/blender/python/generic/Geometry.c +++ b/source/blender/python/generic/Geometry.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: Geometry.c 20922 2009-06-16 07:16:51Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -80,7 +80,7 @@ struct PyMethodDef M_Geometry_methods[] = { #if (PY_VERSION_HEX >= 0x03000000) static struct PyModuleDef M_Geometry_module_def = { - PyModuleDef_HEAD_INIT, + {}, /* m_base */ "Geometry", /* m_name */ M_Geometry_doc, /* m_doc */ 0, /* m_size */ @@ -164,10 +164,6 @@ static PyObject *M_Geometry_PolyFill( PyObject * self, PyObject * polyLineSeq ) for( index = 0; index<len_polypoints; ++index, fp+=3) { polyVec= PySequence_GetItem( polyLine, index ); if(VectorObject_Check(polyVec)) { - - if(!BaseMath_ReadCallback((VectorObject *)polyVec)) - ls_error= 1; - fp[0] = ((VectorObject *)polyVec)->vec[0]; fp[1] = ((VectorObject *)polyVec)->vec[1]; if( ((VectorObject *)polyVec)->size > 2 ) @@ -238,9 +234,6 @@ static PyObject *M_Geometry_LineIntersect2D( PyObject * self, PyObject * args ) return NULL; } - if(!BaseMath_ReadCallback(line_a1) || !BaseMath_ReadCallback(line_a2) || !BaseMath_ReadCallback(line_b1) || !BaseMath_ReadCallback(line_b2)) - return NULL; - a1x= line_a1->vec[0]; a1y= line_a1->vec[1]; a2x= line_a2->vec[0]; @@ -337,10 +330,6 @@ static PyObject *M_Geometry_ClosestPointOnLine( PyObject * self, PyObject * args PyErr_SetString( PyExc_TypeError, "expected 3 vector types\n" ); return NULL; } - - if(!BaseMath_ReadCallback(pt) || !BaseMath_ReadCallback(line_1) || !BaseMath_ReadCallback(line_2)) - return NULL; - /* accept 2d verts */ if (pt->size==3) { VECCOPY(pt_in, pt->vec);} else { pt_in[2]=0.0; VECCOPY2D(pt_in, pt->vec) } @@ -374,9 +363,6 @@ static PyObject *M_Geometry_PointInTriangle2D( PyObject * self, PyObject * args return NULL; } - if(!BaseMath_ReadCallback(pt_vec) || !BaseMath_ReadCallback(tri_p1) || !BaseMath_ReadCallback(tri_p2) || !BaseMath_ReadCallback(tri_p3)) - return NULL; - return PyLong_FromLong(IsectPT2Df(pt_vec->vec, tri_p1->vec, tri_p2->vec, tri_p3->vec)); } @@ -395,9 +381,6 @@ static PyObject *M_Geometry_PointInQuad2D( PyObject * self, PyObject * args ) return NULL; } - if(!BaseMath_ReadCallback(pt_vec) || !BaseMath_ReadCallback(quad_p1) || !BaseMath_ReadCallback(quad_p2) || !BaseMath_ReadCallback(quad_p3) || !BaseMath_ReadCallback(quad_p4)) - return NULL; - return PyLong_FromLong(IsectPQ2Df(pt_vec->vec, quad_p1->vec, quad_p2->vec, quad_p3->vec, quad_p4->vec)); } @@ -517,9 +500,6 @@ static PyObject *M_Geometry_BezierInterp( PyObject * self, PyObject * args ) return NULL; } - if(!BaseMath_ReadCallback(vec_k1) || !BaseMath_ReadCallback(vec_h1) || !BaseMath_ReadCallback(vec_k2) || !BaseMath_ReadCallback(vec_h2)) - return NULL; - dims= MAX4(vec_k1->size, vec_h1->size, vec_h2->size, vec_k2->size); for(i=0; i < vec_k1->size; i++) k1[i]= vec_k1->vec[i]; diff --git a/source/blender/python/generic/Geometry.h b/source/blender/python/generic/Geometry.h index ebfb054c54a..d7292e31fac 100644 --- a/source/blender/python/generic/Geometry.h +++ b/source/blender/python/generic/Geometry.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: Geometry.h 20007 2009-04-30 12:45:13Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/python/generic/Makefile b/source/blender/python/generic/Makefile index 0dbfbd1d102..20cf7f19ec7 100644 --- a/source/blender/python/generic/Makefile +++ b/source/blender/python/generic/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 11904 2007-08-31 16:16:33Z sirdude $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/python/generic/Mathutils.c b/source/blender/python/generic/Mathutils.c index ffb110376b0..3c34a369baf 100644 --- a/source/blender/python/generic/Mathutils.c +++ b/source/blender/python/generic/Mathutils.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: Mathutils.c 20922 2009-06-16 07:16:51Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -96,7 +96,7 @@ struct PyMethodDef M_Mathutils_methods[] = { #if (PY_VERSION_HEX >= 0x03000000) static struct PyModuleDef M_Mathutils_module_def = { - PyModuleDef_HEAD_INIT, + {}, /* m_base */ "Mathutils", /* m_name */ M_Mathutils_doc, /* m_doc */ 0, /* m_size */ @@ -137,12 +137,81 @@ PyObject *Mathutils_Init(const char *from) PyModule_AddObject( submodule, "Euler", (PyObject *)&euler_Type ); PyModule_AddObject( submodule, "Quaternion", (PyObject *)&quaternion_Type ); - mathutils_matrix_vector_cb_index= Mathutils_RegisterCallback(&mathutils_matrix_vector_cb); - return (submodule); } //-----------------------------METHODS---------------------------- +//----------------column_vector_multiplication (internal)--------- +//COLUMN VECTOR Multiplication (Matrix X Vector) +// [1][2][3] [a] +// [4][5][6] * [b] +// [7][8][9] [c] +//vector/matrix multiplication IS NOT COMMUTATIVE!!!! +PyObject *column_vector_multiplication(MatrixObject * mat, VectorObject* vec) +{ + float vecNew[4], vecCopy[4]; + double dot = 0.0f; + int x, y, z = 0; + + if(mat->rowSize != vec->size){ + if(mat->rowSize == 4 && vec->size != 3){ + PyErr_SetString(PyExc_AttributeError, "matrix * vector: matrix row size and vector size must be the same"); + return NULL; + }else{ + vecCopy[3] = 1.0f; + } + } + + for(x = 0; x < vec->size; x++){ + vecCopy[x] = vec->vec[x]; + } + + for(x = 0; x < mat->rowSize; x++) { + for(y = 0; y < mat->colSize; y++) { + dot += mat->matrix[x][y] * vecCopy[y]; + } + vecNew[z++] = (float)dot; + dot = 0.0f; + } + return newVectorObject(vecNew, vec->size, Py_NEW); +} + +//-----------------row_vector_multiplication (internal)----------- +//ROW VECTOR Multiplication - Vector X Matrix +//[x][y][z] * [1][2][3] +// [4][5][6] +// [7][8][9] +//vector/matrix multiplication IS NOT COMMUTATIVE!!!! +PyObject *row_vector_multiplication(VectorObject* vec, MatrixObject * mat) +{ + float vecNew[4], vecCopy[4]; + double dot = 0.0f; + int x, y, z = 0, vec_size = vec->size; + + if(mat->colSize != vec_size){ + if(mat->rowSize == 4 && vec_size != 3){ + PyErr_SetString(PyExc_AttributeError, "vector * matrix: matrix column size and the vector size must be the same"); + return NULL; + }else{ + vecCopy[3] = 1.0f; + } + } + + for(x = 0; x < vec_size; x++){ + vecCopy[x] = vec->vec[x]; + } + + //muliplication + for(x = 0; x < mat->colSize; x++) { + for(y = 0; y < mat->rowSize; y++) { + dot += mat->matrix[y][x] * vecCopy[y]; + } + vecNew[z++] = (float)dot; + dot = 0.0f; + } + return newVectorObject(vecNew, vec_size, Py_NEW); +} + //-----------------quat_rotation (internal)----------- //This function multiplies a vector/point * quat or vice versa //to rotate the point/vector by the quaternion @@ -155,15 +224,8 @@ PyObject *quat_rotation(PyObject *arg1, PyObject *arg2) if(QuaternionObject_Check(arg1)){ quat = (QuaternionObject*)arg1; - if(!BaseMath_ReadCallback(quat)) - return NULL; - if(VectorObject_Check(arg2)){ vec = (VectorObject*)arg2; - - if(!BaseMath_ReadCallback(vec)) - return NULL; - rot[0] = quat->quat[0]*quat->quat[0]*vec->vec[0] + 2*quat->quat[2]*quat->quat[0]*vec->vec[2] - 2*quat->quat[3]*quat->quat[0]*vec->vec[1] + quat->quat[1]*quat->quat[1]*vec->vec[0] + 2*quat->quat[2]*quat->quat[1]*vec->vec[1] + 2*quat->quat[3]*quat->quat[1]*vec->vec[2] - @@ -180,15 +242,8 @@ PyObject *quat_rotation(PyObject *arg1, PyObject *arg2) } }else if(VectorObject_Check(arg1)){ vec = (VectorObject*)arg1; - - if(!BaseMath_ReadCallback(vec)) - return NULL; - if(QuaternionObject_Check(arg2)){ quat = (QuaternionObject*)arg2; - if(!BaseMath_ReadCallback(quat)) - return NULL; - rot[0] = quat->quat[0]*quat->quat[0]*vec->vec[0] + 2*quat->quat[2]*quat->quat[0]*vec->vec[2] - 2*quat->quat[3]*quat->quat[0]*vec->vec[1] + quat->quat[1]*quat->quat[1]*vec->vec[0] + 2*quat->quat[2]*quat->quat[1]*vec->vec[1] + 2*quat->quat[3]*quat->quat[1]*vec->vec[2] - @@ -253,9 +308,6 @@ static PyObject *M_Mathutils_AngleBetweenVecs(PyObject * self, PyObject * args) if(vec1->size != vec2->size) goto AttributeError1; //bad sizes - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2)) - return NULL; - //since size is the same.... size = vec1->size; @@ -275,11 +327,8 @@ static PyObject *M_Mathutils_AngleBetweenVecs(PyObject * self, PyObject * args) angleRads = (double)saacos(dot); -#ifdef USE_MATHUTILS_DEG return PyFloat_FromDouble(angleRads * (180/ Py_PI)); -#else - return PyFloat_FromDouble(angleRads); -#endif + AttributeError1: PyErr_SetString(PyExc_AttributeError, "Mathutils.AngleBetweenVecs(): expects (2) VECTOR objects of the same size\n"); return NULL; @@ -304,9 +353,6 @@ static PyObject *M_Mathutils_MidpointVecs(PyObject * self, PyObject * args) PyErr_SetString(PyExc_AttributeError, "Mathutils.MidpointVecs(): expects (2) vector objects of the same size\n"); return NULL; } - - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2)) - return NULL; for(x = 0; x < vec1->size; x++) { vec[x] = 0.5f * (vec1->vec[x] + vec2->vec[x]); @@ -331,10 +377,6 @@ static PyObject *M_Mathutils_ProjectVecs(PyObject * self, PyObject * args) return NULL; } - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2)) - return NULL; - - //since they are the same size... size = vec1->size; @@ -367,19 +409,12 @@ static PyObject *M_Mathutils_RotationMatrix(PyObject * self, PyObject * args) PyErr_SetString(PyExc_TypeError, "Mathutils.RotationMatrix(): expected float int and optional string and vector\n"); return NULL; } - -#ifdef USE_MATHUTILS_DEG + /* Clamp to -360:360 */ while (angle<-360.0f) angle+=360.0; while (angle>360.0f) angle-=360.0; -#else - while (angle<-(Py_PI*2)) - angle+=(Py_PI*2); - while (angle>(Py_PI*2)) - angle-=(Py_PI*2); -#endif if(matSize != 2 && matSize != 3 && matSize != 4) { PyErr_SetString(PyExc_AttributeError, "Mathutils.RotationMatrix(): can only return a 2x2 3x3 or 4x4 matrix\n"); @@ -404,16 +439,9 @@ static PyObject *M_Mathutils_RotationMatrix(PyObject * self, PyObject * args) PyErr_SetString(PyExc_AttributeError, "Mathutils.RotationMatrix(): the arbitrary axis must be a 3D vector\n"); return NULL; } - - if(!BaseMath_ReadCallback(vec)) - return NULL; - } -#ifdef USE_MATHUTILS_DEG //convert to radians angle = angle * (float) (Py_PI / 180); -#endif - if(axis == NULL && matSize == 2) { //2D rotation matrix mat[0] = (float) cos (angle); @@ -510,10 +538,6 @@ static PyObject *M_Mathutils_TranslationMatrix(PyObject * self, VectorObject * v PyErr_SetString(PyExc_TypeError, "Mathutils.TranslationMatrix(): vector must be 3D or 4D\n"); return NULL; } - - if(!BaseMath_ReadCallback(vec)) - return NULL; - //create a identity matrix and add translation Mat4One((float(*)[4]) mat); mat[12] = vec->vec[0]; @@ -546,10 +570,6 @@ static PyObject *M_Mathutils_ScaleMatrix(PyObject * self, PyObject * args) PyErr_SetString(PyExc_AttributeError, "Mathutils.ScaleMatrix(): please use 2D vectors when scaling in 2D\n"); return NULL; } - - if(!BaseMath_ReadCallback(vec)) - return NULL; - } if(vec == NULL) { //scaling along axis if(matSize == 2) { @@ -625,10 +645,6 @@ static PyObject *M_Mathutils_OrthoProjectionMatrix(PyObject * self, PyObject * a PyErr_SetString(PyExc_AttributeError, "Mathutils.OrthoProjectionMatrix(): please use 2D vectors when scaling in 2D\n"); return NULL; } - - if(!BaseMath_ReadCallback(vec)) - return NULL; - } if(vec == NULL) { //ortho projection onto cardinal plane if(((strcmp(plane, "x") == 0) @@ -785,10 +801,6 @@ static PyObject *M_Mathutils_DifferenceQuats(PyObject * self, PyObject * args) PyErr_SetString(PyExc_TypeError, "Mathutils.DifferenceQuats(): expected Quaternion types"); return NULL; } - - if(!BaseMath_ReadCallback(quatU) || !BaseMath_ReadCallback(quatV)) - return NULL; - tempQuat[0] = quatU->quat[0]; tempQuat[1] = -quatU->quat[1]; tempQuat[2] = -quatU->quat[2]; @@ -816,10 +828,6 @@ static PyObject *M_Mathutils_Slerp(PyObject * self, PyObject * args) PyErr_SetString(PyExc_TypeError, "Mathutils.Slerp(): expected Quaternion types and float"); return NULL; } - - if(!BaseMath_ReadCallback(quatU) || !BaseMath_ReadCallback(quatV)) - return NULL; - if(param > 1.0f || param < 0.0f) { PyErr_SetString(PyExc_AttributeError, "Mathutils.Slerp(): interpolation factor must be between 0.0 and 1.0"); return NULL; @@ -883,9 +891,6 @@ static PyObject *M_Mathutils_Intersect( PyObject * self, PyObject * args ) return NULL; } - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2) || !BaseMath_ReadCallback(vec3) || !BaseMath_ReadCallback(ray) || !BaseMath_ReadCallback(ray_off)) - return NULL; - VECCOPY(v1, vec1->vec); VECCOPY(v2, vec2->vec); VECCOPY(v3, vec3->vec); @@ -954,10 +959,6 @@ static PyObject *M_Mathutils_LineIntersect( PyObject * self, PyObject * args ) PyErr_SetString( PyExc_TypeError,"vectors must be of the same size\n" ); return NULL; } - - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2) || !BaseMath_ReadCallback(vec3) || !BaseMath_ReadCallback(vec4)) - return NULL; - if( vec1->size == 3 || vec1->size == 2) { int result; @@ -1028,10 +1029,6 @@ static PyObject *M_Mathutils_QuadNormal( PyObject * self, PyObject * args ) PyErr_SetString( PyExc_TypeError, "only 3D vectors\n" ); return NULL; } - - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2) || !BaseMath_ReadCallback(vec3) || !BaseMath_ReadCallback(vec4)) - return NULL; - VECCOPY(v1, vec1->vec); VECCOPY(v2, vec2->vec); VECCOPY(v3, vec3->vec); @@ -1076,9 +1073,6 @@ static PyObject *M_Mathutils_TriangleNormal( PyObject * self, PyObject * args ) PyErr_SetString( PyExc_TypeError, "only 3D vectors\n" ); return NULL; } - - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2) || !BaseMath_ReadCallback(vec3)) - return NULL; VECCOPY(v1, vec1->vec); VECCOPY(v2, vec2->vec); @@ -1111,9 +1105,6 @@ static PyObject *M_Mathutils_TriangleArea( PyObject * self, PyObject * args ) PyErr_SetString( PyExc_TypeError, "vectors must be of the same size\n" ); return NULL; } - - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2) || !BaseMath_ReadCallback(vec3)) - return NULL; if (vec1->size == 3) { VECCOPY(v1, vec1->vec); @@ -1163,8 +1154,8 @@ int EXPP_FloatsAreEqual(float A, float B, int floatSteps) } /*---------------------- EXPP_VectorsAreEqual ------------------------- Builds on EXPP_FloatsAreEqual to test vectors */ -int EXPP_VectorsAreEqual(float *vecA, float *vecB, int size, int floatSteps) -{ +int EXPP_VectorsAreEqual(float *vecA, float *vecB, int size, int floatSteps){ + int x; for (x=0; x< size; x++){ if (EXPP_FloatsAreEqual(vecA[x], vecB[x], floatSteps) == 0) @@ -1174,86 +1165,6 @@ int EXPP_VectorsAreEqual(float *vecA, float *vecB, int size, int floatSteps) } -/* Mathutils Callbacks */ - -/* for mathutils internal use only, eventually should re-alloc but to start with we only have a few users */ -Mathutils_Callback *mathutils_callbacks[8] = {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}; - -int Mathutils_RegisterCallback(Mathutils_Callback *cb) -{ - int i; - - /* find the first free slot */ - for(i= 0; mathutils_callbacks[i]; i++) { - if(mathutils_callbacks[i]==cb) /* alredy registered? */ - return i; - } - - mathutils_callbacks[i] = cb; - return i; -} - -/* use macros to check for NULL */ -int _BaseMathObject_ReadCallback(BaseMathObject *self) -{ - Mathutils_Callback *cb= mathutils_callbacks[self->cb_type]; - if(cb->get(self->cb_user, self->cb_subtype, self->data)) - return 1; - - PyErr_Format(PyExc_SystemError, "%s user has become invalid", Py_TYPE(self)->tp_name); - return 0; -} - -int _BaseMathObject_WriteCallback(BaseMathObject *self) -{ - Mathutils_Callback *cb= mathutils_callbacks[self->cb_type]; - if(cb->set(self->cb_user, self->cb_subtype, self->data)) - return 1; - - PyErr_Format(PyExc_SystemError, "%s user has become invalid", Py_TYPE(self)->tp_name); - return 0; -} - -int _BaseMathObject_ReadIndexCallback(BaseMathObject *self, int index) -{ - Mathutils_Callback *cb= mathutils_callbacks[self->cb_type]; - if(cb->get_index(self->cb_user, self->cb_subtype, self->data, index)) - return 1; - - PyErr_Format(PyExc_SystemError, "%s user has become invalid", Py_TYPE(self)->tp_name); - return 0; -} - -int _BaseMathObject_WriteIndexCallback(BaseMathObject *self, int index) -{ - Mathutils_Callback *cb= mathutils_callbacks[self->cb_type]; - if(cb->set_index(self->cb_user, self->cb_subtype, self->data, index)) - return 1; - - PyErr_Format(PyExc_SystemError, "%s user has become invalid", Py_TYPE(self)->tp_name); - return 0; -} - -/* BaseMathObject generic functions for all mathutils types */ -PyObject *BaseMathObject_getOwner( BaseMathObject * self, void *type ) -{ - PyObject *ret= self->cb_user ? self->cb_user : Py_None; - Py_INCREF(ret); - return ret; -} - -PyObject *BaseMathObject_getWrapped( BaseMathObject *self, void *type ) -{ - return PyBool_FromLong((self->wrapped == Py_WRAP) ? 1:0); -} - -void BaseMathObject_dealloc(BaseMathObject * self) -{ - /* only free non wrapped */ - if(self->wrapped != Py_WRAP) - PyMem_Free(self->data); - - Py_XDECREF(self->cb_user); - PyObject_DEL(self); -} +//####################################################################### +//#############################DEPRECATED################################ diff --git a/source/blender/python/generic/Mathutils.h b/source/blender/python/generic/Mathutils.h index 6a4e28d6068..e8882c3dac2 100644 --- a/source/blender/python/generic/Mathutils.h +++ b/source/blender/python/generic/Mathutils.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: Mathutils.h 20332 2009-05-22 03:22:56Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -38,28 +38,10 @@ #include "quat.h" #include "euler.h" -/* #define USE_MATHUTILS_DEG - for backwards compat */ - -/* Can cast different mathutils types to this, use for generic funcs */ - -typedef struct { - PyObject_VAR_HEAD - float *data; /*array of data (alias), wrapped status depends on wrapped status */ - PyObject *cb_user; /* if this vector references another object, otherwise NULL, *Note* this owns its reference */ - unsigned char cb_type; /* which user funcs do we adhere to, RNA, GameObject, etc */ - unsigned char cb_subtype; /* subtype: location, rotation... to avoid defining many new functions for every attribute of the same type */ - unsigned char wrapped; /* wrapped data type? */ -} BaseMathObject; - -PyObject *BaseMathObject_getOwner( BaseMathObject * self, void * ); -PyObject *BaseMathObject_getWrapped( BaseMathObject *self, void * ); -void BaseMathObject_dealloc(BaseMathObject * self); - - - - PyObject *Mathutils_Init( const char * from ); +PyObject *row_vector_multiplication(VectorObject* vec, MatrixObject * mat); +PyObject *column_vector_multiplication(MatrixObject * mat, VectorObject* vec); PyObject *quat_rotation(PyObject *arg1, PyObject *arg2); int EXPP_FloatsAreEqual(float A, float B, int floatSteps); @@ -67,9 +49,8 @@ int EXPP_VectorsAreEqual(float *vecA, float *vecB, int size, int floatSteps); #define Py_PI 3.14159265358979323846 - -#define Py_NEW 1 -#define Py_WRAP 2 +#define Py_WRAP 1024 +#define Py_NEW 2048 /* Mathutils is used by the BGE and Blender so have to define @@ -84,26 +65,4 @@ int EXPP_VectorsAreEqual(float *vecA, float *vecB, int size, int floatSteps); #define Py_RETURN_TRUE return Py_INCREF(Py_True), Py_True #endif -typedef struct Mathutils_Callback Mathutils_Callback; -struct Mathutils_Callback { - int (*check)(PyObject *user); /* checks the user is still valid */ - int (*get)(PyObject *user, int subtype, float *from); /* gets the vector from the user */ - int (*set)(PyObject *user, int subtype, float *to); /* sets the users vector values once the vector is modified */ - int (*get_index)(PyObject *user, int subtype, float *from,int index); /* same as above but only for an index */ - int (*set_index)(PyObject *user, int subtype, float *to, int index); /* same as above but only for an index */ -}; - -int Mathutils_RegisterCallback(Mathutils_Callback *cb); - -int _BaseMathObject_ReadCallback(BaseMathObject *self); -int _BaseMathObject_WriteCallback(BaseMathObject *self); -int _BaseMathObject_ReadIndexCallback(BaseMathObject *self, int index); -int _BaseMathObject_WriteIndexCallback(BaseMathObject *self, int index); - -/* since this is called so often avoid where possible */ -#define BaseMath_ReadCallback(_self) (((_self)->cb_user ? _BaseMathObject_ReadCallback((BaseMathObject *)_self):1)) -#define BaseMath_WriteCallback(_self) (((_self)->cb_user ?_BaseMathObject_WriteCallback((BaseMathObject *)_self):1)) -#define BaseMath_ReadIndexCallback(_self, _index) (((_self)->cb_user ? _BaseMathObject_ReadIndexCallback((BaseMathObject *)_self, _index):1)) -#define BaseMath_WriteIndexCallback(_self, _index) (((_self)->cb_user ? _BaseMathObject_WriteIndexCallback((BaseMathObject *)_self, _index):1)) - #endif /* EXPP_Mathutils_H */ diff --git a/source/blender/python/generic/bpy_internal_import.c b/source/blender/python/generic/bpy_internal_import.c index c41ea386c0e..6789aea9c10 100644 --- a/source/blender/python/generic/bpy_internal_import.c +++ b/source/blender/python/generic/bpy_internal_import.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: bpy_internal_import.c 20434 2009-05-26 18:06:09Z campbellbarton $ * ***** BEGIN GPL LICENSE BLOCK ***** * * This program is free software; you can redistribute it and/or diff --git a/source/blender/python/generic/bpy_internal_import.h b/source/blender/python/generic/bpy_internal_import.h index aeeafb7c1c4..475ec8dd118 100644 --- a/source/blender/python/generic/bpy_internal_import.h +++ b/source/blender/python/generic/bpy_internal_import.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: bpy_internal_import.h 20434 2009-05-26 18:06:09Z campbellbarton $ * ***** BEGIN GPL LICENSE BLOCK ***** * * This program is free software; you can redistribute it and/or diff --git a/source/blender/python/generic/euler.c b/source/blender/python/generic/euler.c index 769c82ed034..a65feb7e949 100644 --- a/source/blender/python/generic/euler.c +++ b/source/blender/python/generic/euler.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: euler.c 20248 2009-05-18 04:11:54Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -65,12 +65,12 @@ static struct PyMethodDef Euler_methods[] = { //----------------------------------Mathutils.Euler() ------------------- //makes a new euler for you to play with -static PyObject *Euler_new(PyObject * self, PyObject * args, PyObject * kwargs) +static PyObject *Euler_new(PyObject * self, PyObject * args) { PyObject *listObject = NULL; int size, i; - float eul[3]; + float eul[3], scalar; PyObject *e; size = PyTuple_GET_SIZE(args); @@ -102,13 +102,15 @@ static PyObject *Euler_new(PyObject * self, PyObject * args, PyObject * kwargs) return NULL; } - eul[i]= (float)PyFloat_AsDouble(e); + scalar= (float)PyFloat_AsDouble(e); Py_DECREF(e); - if(eul[i]==-1 && PyErr_Occurred()) { // parsed item is not a number + if(scalar==-1 && PyErr_Occurred()) { // parsed item is not a number PyErr_SetString(PyExc_TypeError, "Mathutils.Euler(): 3d numeric sequence expected\n"); return NULL; } + + eul[i]= scalar; } return newEulerObject(eul, Py_NEW); } @@ -121,18 +123,10 @@ static PyObject *Euler_ToQuat(EulerObject * self) float eul[3], quat[4]; int x; - if(!BaseMath_ReadCallback(self)) - return NULL; - -#ifdef USE_MATHUTILS_DEG for(x = 0; x < 3; x++) { eul[x] = self->eul[x] * ((float)Py_PI / 180); } EulToQuat(eul, quat); -#else - EulToQuat(self->eul, quat); -#endif - return newQuaternionObject(quat, Py_NEW); } //----------------------------Euler.toMatrix()--------------------- @@ -143,17 +137,10 @@ static PyObject *Euler_ToMatrix(EulerObject * self) float mat[9] = {0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f}; int x; - if(!BaseMath_ReadCallback(self)) - return NULL; - -#ifdef USE_MATHUTILS_DEG for(x = 0; x < 3; x++) { eul[x] = self->eul[x] * ((float)Py_PI / 180); } EulToMat3(eul, (float (*)[3]) mat); -#else - EulToMat3(self->eul, (float (*)[3]) mat); -#endif return newMatrixObject(mat, 3, 3 , Py_NEW); } //----------------------------Euler.unique()----------------------- @@ -165,20 +152,10 @@ static PyObject *Euler_Unique(EulerObject * self) double piO2 = Py_PI / 2.0f; double Opi2 = 1.0f / pi2; - if(!BaseMath_ReadCallback(self)) - return NULL; - -#ifdef USE_MATHUTILS_DEG //radians heading = self->eul[0] * (float)Py_PI / 180; pitch = self->eul[1] * (float)Py_PI / 180; bank = self->eul[2] * (float)Py_PI / 180; -#else - heading = self->eul[0]; - pitch = self->eul[1]; - bank = self->eul[2]; -#endif - //wrap heading in +180 / -180 pitch += Py_PI; @@ -209,14 +186,11 @@ static PyObject *Euler_Unique(EulerObject * self) heading -= (floor(heading * Opi2)) * pi2; heading -= Py_PI; -#ifdef USE_MATHUTILS_DEG //back to degrees self->eul[0] = (float)(heading * 180 / (float)Py_PI); self->eul[1] = (float)(pitch * 180 / (float)Py_PI); self->eul[2] = (float)(bank * 180 / (float)Py_PI); -#endif - BaseMath_WriteCallback(self); Py_INCREF(self); return (PyObject *)self; } @@ -228,7 +202,6 @@ static PyObject *Euler_Zero(EulerObject * self) self->eul[1] = 0.0; self->eul[2] = 0.0; - BaseMath_WriteCallback(self); Py_INCREF(self); return (PyObject *)self; } @@ -250,63 +223,42 @@ static PyObject *Euler_Rotate(EulerObject * self, PyObject *args) return NULL; } - if(!BaseMath_ReadCallback(self)) - return NULL; - -#ifdef USE_MATHUTILS_DEG //covert to radians angle *= ((float)Py_PI / 180); for(x = 0; x < 3; x++) { self->eul[x] *= ((float)Py_PI / 180); } -#endif euler_rot(self->eul, angle, *axis); - -#ifdef USE_MATHUTILS_DEG //convert back from radians for(x = 0; x < 3; x++) { self->eul[x] *= (180 / (float)Py_PI); } -#endif - BaseMath_WriteCallback(self); Py_INCREF(self); return (PyObject *)self; } static PyObject *Euler_MakeCompatible(EulerObject * self, EulerObject *value) { -#ifdef USE_MATHUTILS_DEG float eul_from_rad[3]; int x; -#endif if(!EulerObject_Check(value)) { PyErr_SetString(PyExc_TypeError, "euler.makeCompatible(euler):expected a single euler argument."); return NULL; } - if(!BaseMath_ReadCallback(self) || !BaseMath_ReadCallback(value)) - return NULL; - -#ifdef USE_MATHUTILS_DEG //covert to radians for(x = 0; x < 3; x++) { self->eul[x] = self->eul[x] * ((float)Py_PI / 180); eul_from_rad[x] = value->eul[x] * ((float)Py_PI / 180); } compatible_eul(self->eul, eul_from_rad); -#else - compatible_eul(self->eul, value->eul); -#endif - -#ifdef USE_MATHUTILS_DEG //convert back from radians for(x = 0; x < 3; x++) { self->eul[x] *= (180 / (float)Py_PI); } -#endif - BaseMath_WriteCallback(self); + Py_INCREF(self); return (PyObject *)self; } @@ -315,21 +267,26 @@ static PyObject *Euler_MakeCompatible(EulerObject * self, EulerObject *value) // return a copy of the euler static PyObject *Euler_copy(EulerObject * self, PyObject *args) { - if(!BaseMath_ReadCallback(self)) - return NULL; - return newEulerObject(self->eul, Py_NEW); } + +//----------------------------dealloc()(internal) ------------------ +//free the py_object +static void Euler_dealloc(EulerObject * self) +{ + //only free py_data + if(self->data.py_data){ + PyMem_Free(self->data.py_data); + } + PyObject_DEL(self); +} + //----------------------------print object (internal)-------------- //print the object to screen static PyObject *Euler_repr(EulerObject * self) { char str[64]; - - if(!BaseMath_ReadCallback(self)) - return NULL; - sprintf(str, "[%.6f, %.6f, %.6f](euler)", self->eul[0], self->eul[1], self->eul[2]); return PyUnicode_FromString(str); } @@ -340,18 +297,7 @@ static PyObject* Euler_richcmpr(PyObject *objectA, PyObject *objectB, int compar EulerObject *eulA = NULL, *eulB = NULL; int result = 0; - if(EulerObject_Check(objectA)) { - eulA = (EulerObject*)objectA; - if(!BaseMath_ReadCallback(eulA)) - return NULL; - } - if(EulerObject_Check(objectB)) { - eulB = (EulerObject*)objectB; - if(!BaseMath_ReadCallback(eulB)) - return NULL; - } - - if (!eulA || !eulB){ + if (!EulerObject_Check(objectA) || !EulerObject_Check(objectB)){ if (comparison_type == Py_NE){ Py_RETURN_TRUE; }else{ @@ -396,16 +342,13 @@ static int Euler_len(EulerObject * self) //sequence accessor (get) static PyObject *Euler_item(EulerObject * self, int i) { - if(i<0) i= 3-i; + if(i<0) + i= 3-i; if(i < 0 || i >= 3) { PyErr_SetString(PyExc_IndexError, "euler[attribute]: array index out of range"); return NULL; } - - if(!BaseMath_ReadIndexCallback(self, i)) - return NULL; - return PyFloat_FromDouble(self->eul[i]); } @@ -420,7 +363,8 @@ static int Euler_ass_item(EulerObject * self, int i, PyObject * value) return -1; } - if(i<0) i= 3-i; + if(i<0) + i= 3-i; if(i < 0 || i >= 3){ PyErr_SetString(PyExc_IndexError, "euler[attribute] = x: array assignment index out of range\n"); @@ -428,10 +372,6 @@ static int Euler_ass_item(EulerObject * self, int i, PyObject * value) } self->eul[i] = f; - - if(!BaseMath_WriteIndexCallback(self, i)) - return -1; - return 0; } //----------------------------object[z:y]------------------------ @@ -441,9 +381,6 @@ static PyObject *Euler_slice(EulerObject * self, int begin, int end) PyObject *list = NULL; int count; - if(!BaseMath_ReadCallback(self)) - return NULL; - CLAMP(begin, 0, 3); if (end<0) end= 4+end; CLAMP(end, 0, 3); @@ -464,10 +401,7 @@ static int Euler_ass_slice(EulerObject * self, int begin, int end, { int i, y, size = 0; float eul[3]; - PyObject *e; - - if(!BaseMath_ReadCallback(self)) - return -1; + PyObject *e, *f; CLAMP(begin, 0, 3); if (end<0) end= 4+end; @@ -487,20 +421,21 @@ static int Euler_ass_slice(EulerObject * self, int begin, int end, return -1; } - eul[i] = (float)PyFloat_AsDouble(e); - Py_DECREF(e); - - if(eul[i]==-1 && PyErr_Occurred()) { // parsed item not a number + f = PyNumber_Float(e); + if(f == NULL) { // parsed item not a number + Py_DECREF(e); PyErr_SetString(PyExc_TypeError, "euler[begin:end] = []: sequence argument not a number"); return -1; } + + eul[i] = (float)PyFloat_AS_DOUBLE(f); + Py_DECREF(f); + Py_DECREF(e); } //parsed well - now set in vector for(y = 0; y < 3; y++){ self->eul[begin + y] = eul[y]; } - - BaseMath_WriteCallback(self); return 0; } //-----------------PROTCOL DECLARATIONS-------------------------- @@ -515,30 +450,79 @@ static PySequenceMethods Euler_SeqMethods = { }; + /* * vector axis, vector.x/y/z/w */ static PyObject *Euler_getAxis( EulerObject * self, void *type ) { - return Euler_item(self, GET_INT_FROM_POINTER(type)); + switch( (long)type ) { + case 'X': /* these are backwards, but that how it works */ + return PyFloat_FromDouble(self->eul[0]); + case 'Y': + return PyFloat_FromDouble(self->eul[1]); + case 'Z': + return PyFloat_FromDouble(self->eul[2]); + } + + PyErr_SetString(PyExc_SystemError, "corrupt euler, cannot get axis"); + return NULL; } static int Euler_setAxis( EulerObject * self, PyObject * value, void * type ) { - return Euler_ass_item(self, GET_INT_FROM_POINTER(type), value); + float param= (float)PyFloat_AsDouble( value ); + + if (param==-1 && PyErr_Occurred()) { + PyErr_SetString(PyExc_TypeError, "expected a number for the vector axis"); + return -1; + } + + switch( (long)type ) { + case 'X': /* these are backwards, but that how it works */ + self->eul[0]= param; + break; + case 'Y': + self->eul[1]= param; + break; + case 'Z': + self->eul[2]= param; + break; + } + + return 0; +} + +static PyObject *Euler_getWrapped( VectorObject * self, void *type ) +{ + if (self->wrapped == Py_WRAP) + Py_RETURN_TRUE; + else + Py_RETURN_FALSE; } + /*****************************************************************************/ /* Python attributes get/set structure: */ /*****************************************************************************/ static PyGetSetDef Euler_getseters[] = { - {"x", (getter)Euler_getAxis, (setter)Euler_setAxis, "Euler X axis", (void *)0}, - {"y", (getter)Euler_getAxis, (setter)Euler_setAxis, "Euler Y axis", (void *)1}, - {"z", (getter)Euler_getAxis, (setter)Euler_setAxis, "Euler Z axis", (void *)2}, - - {"wrapped", (getter)BaseMathObject_getWrapped, (setter)NULL, "True when this wraps blenders internal data", NULL}, - {"__owner__", (getter)BaseMathObject_getOwner, (setter)NULL, "Read only owner for vectors that depend on another object", NULL}, + {"x", + (getter)Euler_getAxis, (setter)Euler_setAxis, + "Euler X axis", + (void *)'X'}, + {"y", + (getter)Euler_getAxis, (setter)Euler_setAxis, + "Euler Y axis", + (void *)'Y'}, + {"z", + (getter)Euler_getAxis, (setter)Euler_setAxis, + "Euler Z axis", + (void *)'Z'}, + {"wrapped", + (getter)Euler_getWrapped, (setter)NULL, + "True when this wraps blenders internal data", + NULL}, {NULL,NULL,NULL,NULL,NULL} /* Sentinel */ }; @@ -554,7 +538,7 @@ PyTypeObject euler_Type = { "euler", //tp_name sizeof(EulerObject), //tp_basicsize 0, //tp_itemsize - (destructor)BaseMathObject_dealloc, //tp_dealloc + (destructor)Euler_dealloc, //tp_dealloc 0, //tp_print 0, //tp_getattr 0, //tp_setattr @@ -609,22 +593,24 @@ PyObject *newEulerObject(float *eul, int type) int x; self = PyObject_NEW(EulerObject, &euler_Type); - - /* init callbacks as NULL */ - self->cb_user= NULL; - self->cb_type= self->cb_subtype= 0; + self->data.blend_data = NULL; + self->data.py_data = NULL; if(type == Py_WRAP){ - self->eul = eul; + self->data.blend_data = eul; + self->eul = self->data.blend_data; self->wrapped = Py_WRAP; }else if (type == Py_NEW){ - self->eul = PyMem_Malloc(3 * sizeof(float)); + self->data.py_data = PyMem_Malloc(3 * sizeof(float)); + self->eul = self->data.py_data; if(!eul) { //new empty for(x = 0; x < 3; x++) { self->eul[x] = 0.0f; } }else{ - VECCOPY(self->eul, eul); + for(x = 0; x < 3; x++){ + self->eul[x] = eul[x]; + } } self->wrapped = Py_NEW; }else{ //bad type @@ -632,16 +618,3 @@ PyObject *newEulerObject(float *eul, int type) } return (PyObject *)self; } - -PyObject *newEulerObject_cb(PyObject *cb_user, int cb_type, int cb_subtype) -{ - EulerObject *self= (EulerObject *)newEulerObject(NULL, Py_NEW); - if(self) { - Py_INCREF(cb_user); - self->cb_user= cb_user; - self->cb_type= (unsigned char)cb_type; - self->cb_subtype= (unsigned char)cb_subtype; - } - - return (PyObject *)self; -} diff --git a/source/blender/python/generic/euler.h b/source/blender/python/generic/euler.h index 0bff6de6964..3206668ffa0 100644 --- a/source/blender/python/generic/euler.h +++ b/source/blender/python/generic/euler.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: euler.h 20248 2009-05-18 04:11:54Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -40,13 +40,12 @@ extern PyTypeObject euler_Type; typedef struct { PyObject_VAR_HEAD - float *eul; /*1D array of data */ - PyObject *cb_user; /* if this vector references another object, otherwise NULL, *Note* this owns its reference */ - unsigned char cb_type; /* which user funcs do we adhere to, RNA, GameObject, etc */ - unsigned char cb_subtype; /* subtype: location, rotation... to avoid defining many new functions for every attribute of the same type */ - unsigned char wrapped; /* wrapped data type? */ - /* end BaseMathObject */ - + struct{ + float *py_data; //python managed + float *blend_data; //blender managed + }data; + float *eul; //1D array of data (alias) + int wrapped; //is wrapped data? } EulerObject; /*struct data contains a pointer to the actual data that the @@ -56,6 +55,5 @@ blender (stored in blend_data). This is an either/or struct not both*/ //prototypes PyObject *newEulerObject( float *eul, int type ); -PyObject *newEulerObject_cb(PyObject *cb_user, int cb_type, int cb_subtype); #endif /* EXPP_euler_h */ diff --git a/source/blender/python/generic/matrix.c b/source/blender/python/generic/matrix.c index 311a14fbb0a..e2ab1c3c653 100644 --- a/source/blender/python/generic/matrix.c +++ b/source/blender/python/generic/matrix.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: matrix.c 20249 2009-05-18 04:27:48Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -31,71 +31,6 @@ #include "BLI_arithb.h" #include "BLI_blenlib.h" -static PyObject *column_vector_multiplication(MatrixObject * mat, VectorObject* vec); /* utility func */ - - -/* matrix vector callbacks */ -int mathutils_matrix_vector_cb_index= -1; - -static int mathutils_matrix_vector_check(MatrixObject *self) -{ - return BaseMath_ReadCallback(self); -} - -static int mathutils_matrix_vector_get(MatrixObject *self, int subtype, float *vec_from) -{ - int i; - if(!BaseMath_ReadCallback(self)) - return 0; - - for(i=0; i<self->colSize; i++) - vec_from[i]= self->matrix[subtype][i]; - - return 1; -} - -static int mathutils_matrix_vector_set(MatrixObject *self, int subtype, float *vec_to) -{ - int i; - if(!BaseMath_ReadCallback(self)) - return 0; - - for(i=0; i<self->colSize; i++) - self->matrix[subtype][i]= vec_to[i]; - - BaseMath_WriteCallback(self); - return 1; -} - -static int mathutils_matrix_vector_get_index(MatrixObject *self, int subtype, float *vec_from, int index) -{ - if(!BaseMath_ReadCallback(self)) - return 0; - - vec_from[index]= self->matrix[subtype][index]; - return 1; -} - -static int mathutils_matrix_vector_set_index(MatrixObject *self, int subtype, float *vec_to, int index) -{ - if(!BaseMath_ReadCallback(self)) - return 0; - - self->matrix[subtype][index]= vec_to[index]; - - BaseMath_WriteCallback(self); - return 1; -} - -Mathutils_Callback mathutils_matrix_vector_cb = { - mathutils_matrix_vector_check, - mathutils_matrix_vector_get, - mathutils_matrix_vector_set, - mathutils_matrix_vector_get_index, - mathutils_matrix_vector_set_index -}; -/* matrix vector callbacks, this is so you can do matrix[i][j] = val */ - /*-------------------------DOC STRINGS ---------------------------*/ static char Matrix_Zero_doc[] = "() - set all values in the matrix to 0"; static char Matrix_Identity_doc[] = "() - set the square matrix to it's identity matrix"; @@ -164,8 +99,6 @@ static PyObject *Matrix_new(PyTypeObject *type, PyObject *args, PyObject *kwds) argObject = PyTuple_GET_ITEM(args, 0); if(MatrixObject_Check(argObject)){ mat = (MatrixObject*)argObject; - if(!BaseMath_ReadCallback(mat)) - return NULL; argSize = mat->rowSize; //rows seqSize = mat->colSize; //col @@ -225,9 +158,6 @@ static PyObject *Matrix_toQuat(MatrixObject * self) { float quat[4]; - if(!BaseMath_ReadCallback(self)) - return NULL; - /*must be 3-4 cols, 3-4 rows, square matrix*/ if(self->colSize < 3 || self->rowSize < 3 || (self->colSize != self->rowSize)) { PyErr_SetString(PyExc_AttributeError, "Matrix.toQuat(): inappropriate matrix size - expects 3x3 or 4x4 matrix"); @@ -248,23 +178,13 @@ PyObject *Matrix_toEuler(MatrixObject * self, PyObject *args) EulerObject *eul_compat = NULL; int x; - if(!BaseMath_ReadCallback(self)) - return NULL; - if(!PyArg_ParseTuple(args, "|O!:toEuler", &euler_Type, &eul_compat)) return NULL; if(eul_compat) { - if(!BaseMath_ReadCallback(eul_compat)) - return NULL; - -#ifdef USE_MATHUTILS_DEG for(x = 0; x < 3; x++) { eul_compatf[x] = eul_compat->eul[x] * ((float)Py_PI / 180); } -#else - VECCOPY(eul_compatf, eul_compat->eul); -#endif } /*must be 3-4 cols, 3-4 rows, square matrix*/ @@ -282,12 +202,10 @@ PyObject *Matrix_toEuler(MatrixObject * self, PyObject *args) PyErr_SetString(PyExc_AttributeError, "Matrix.toEuler(): inappropriate matrix size - expects 3x3 or 4x4 matrix\n"); return NULL; } -#ifdef USE_MATHUTILS_DEG /*have to convert to degrees*/ for(x = 0; x < 3; x++) { eul[x] *= (float) (180 / Py_PI); } -#endif return newEulerObject(eul, Py_NEW); } /*---------------------------Matrix.resize4x4() ------------------*/ @@ -295,20 +213,17 @@ PyObject *Matrix_Resize4x4(MatrixObject * self) { int x, first_row_elem, curr_pos, new_pos, blank_columns, blank_rows, index; - if(self->wrapped==Py_WRAP){ - PyErr_SetString(PyExc_TypeError, "cannot resize wrapped data - make a copy and resize that"); - return NULL; - } - if(self->cb_user){ - PyErr_SetString(PyExc_TypeError, "cannot resize owned data - make a copy and resize that"); + if(self->data.blend_data){ + PyErr_SetString(PyExc_TypeError, "cannot resize wrapped data - only python matrices"); return NULL; } - - self->contigPtr = PyMem_Realloc(self->contigPtr, (sizeof(float) * 16)); - if(self->contigPtr == NULL) { + + self->data.py_data = PyMem_Realloc(self->data.py_data, (sizeof(float) * 16)); + if(self->data.py_data == NULL) { PyErr_SetString(PyExc_MemoryError, "matrix.resize4x4(): problem allocating pointer space"); return NULL; } + self->contigPtr = self->data.py_data; /*force*/ self->matrix = PyMem_Realloc(self->matrix, (sizeof(float *) * 4)); if(self->matrix == NULL) { PyErr_SetString(PyExc_MemoryError, "matrix.resize4x4(): problem allocating pointer space"); @@ -351,10 +266,7 @@ PyObject *Matrix_Resize4x4(MatrixObject * self) PyObject *Matrix_TranslationPart(MatrixObject * self) { float vec[4]; - - if(!BaseMath_ReadCallback(self)) - return NULL; - + if(self->colSize < 3 || self->rowSize < 4){ PyErr_SetString(PyExc_AttributeError, "Matrix.translationPart: inappropriate matrix size"); return NULL; @@ -372,9 +284,6 @@ PyObject *Matrix_RotationPart(MatrixObject * self) float mat[16] = {0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f}; - if(!BaseMath_ReadCallback(self)) - return NULL; - if(self->colSize < 3 || self->rowSize < 3){ PyErr_SetString(PyExc_AttributeError, "Matrix.rotationPart: inappropriate matrix size\n"); return NULL; @@ -398,9 +307,6 @@ PyObject *Matrix_scalePart(MatrixObject * self) float scale[3], rot[3]; float mat[3][3], imat[3][3], tmat[3][3]; - if(!BaseMath_ReadCallback(self)) - return NULL; - /*must be 3-4 cols, 3-4 rows, square matrix*/ if(self->colSize == 4 && self->rowSize == 4) Mat3CpyMat4(mat, (float (*)[4])*self->matrix); @@ -431,9 +337,6 @@ PyObject *Matrix_Invert(MatrixObject * self) float mat[16] = {0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f}; - if(!BaseMath_ReadCallback(self)) - return NULL; - if(self->rowSize != self->colSize){ PyErr_SetString(PyExc_AttributeError, "Matrix.invert(ed): only square matrices are supported"); return NULL; @@ -474,7 +377,6 @@ PyObject *Matrix_Invert(MatrixObject * self) return NULL; } - BaseMath_WriteCallback(self); Py_INCREF(self); return (PyObject *)self; } @@ -485,9 +387,6 @@ PyObject *Matrix_Determinant(MatrixObject * self) { float det = 0.0f; - if(!BaseMath_ReadCallback(self)) - return NULL; - if(self->rowSize != self->colSize){ PyErr_SetString(PyExc_AttributeError, "Matrix.determinant: only square matrices are supported"); return NULL; @@ -513,9 +412,6 @@ PyObject *Matrix_Transpose(MatrixObject * self) { float t = 0.0f; - if(!BaseMath_ReadCallback(self)) - return NULL; - if(self->rowSize != self->colSize){ PyErr_SetString(PyExc_AttributeError, "Matrix.transpose(d): only square matrices are supported"); return NULL; @@ -531,7 +427,6 @@ PyObject *Matrix_Transpose(MatrixObject * self) Mat4Transp((float (*)[4])*self->matrix); } - BaseMath_WriteCallback(self); Py_INCREF(self); return (PyObject *)self; } @@ -541,25 +436,18 @@ PyObject *Matrix_Transpose(MatrixObject * self) PyObject *Matrix_Zero(MatrixObject * self) { int row, col; - + for(row = 0; row < self->rowSize; row++) { for(col = 0; col < self->colSize; col++) { self->matrix[row][col] = 0.0f; } } - - if(!BaseMath_WriteCallback(self)) - return NULL; - Py_INCREF(self); return (PyObject *)self; } /*---------------------------Matrix.identity(() ------------------*/ PyObject *Matrix_Identity(MatrixObject * self) { - if(!BaseMath_ReadCallback(self)) - return NULL; - if(self->rowSize != self->colSize){ PyErr_SetString(PyExc_AttributeError, "Matrix.identity: only square matrices are supported\n"); return NULL; @@ -576,9 +464,6 @@ PyObject *Matrix_Identity(MatrixObject * self) Mat4One((float (*)[4]) *self->matrix); } - if(!BaseMath_WriteCallback(self)) - return NULL; - Py_INCREF(self); return (PyObject *)self; } @@ -586,12 +471,21 @@ PyObject *Matrix_Identity(MatrixObject * self) /*---------------------------Matrix.inverted() ------------------*/ PyObject *Matrix_copy(MatrixObject * self) { - if(!BaseMath_ReadCallback(self)) - return NULL; - return (PyObject*)(MatrixObject*)newMatrixObject((float (*))*self->matrix, self->rowSize, self->colSize, Py_NEW); } +/*----------------------------dealloc()(internal) ----------------*/ +/*free the py_object*/ +static void Matrix_dealloc(MatrixObject * self) +{ + PyMem_Free(self->matrix); + /*only free py_data*/ + if(self->data.py_data){ + PyMem_Free(self->data.py_data); + } + PyObject_DEL(self); +} + /*----------------------------print object (internal)-------------*/ /*print the object to screen*/ static PyObject *Matrix_repr(MatrixObject * self) @@ -599,9 +493,6 @@ static PyObject *Matrix_repr(MatrixObject * self) int x, y; char buffer[48], str[1024]; - if(!BaseMath_ReadCallback(self)) - return NULL; - BLI_strncpy(str,"",1024); for(x = 0; x < self->rowSize; x++){ sprintf(buffer, "["); @@ -638,9 +529,6 @@ static PyObject* Matrix_richcmpr(PyObject *objectA, PyObject *objectB, int compa matA = (MatrixObject*)objectA; matB = (MatrixObject*)objectB; - if(!BaseMath_ReadCallback(matA) || !BaseMath_ReadCallback(matB)) - return NULL; - if (matA->colSize != matB->colSize || matA->rowSize != matB->rowSize){ if (comparison_type == Py_NE){ Py_RETURN_TRUE; @@ -688,14 +576,11 @@ static int Matrix_len(MatrixObject * self) the wrapped vector gives direct access to the matrix data*/ static PyObject *Matrix_item(MatrixObject * self, int i) { - if(!BaseMath_ReadCallback(self)) - return NULL; - if(i < 0 || i >= self->rowSize) { PyErr_SetString(PyExc_IndexError, "matrix[attribute]: array index out of range"); return NULL; } - return newVectorObject_cb((PyObject *)self, self->colSize, mathutils_matrix_vector_cb_index, i); + return newVectorObject(self->matrix[i], self->colSize, Py_WRAP); } /*----------------------------object[]------------------------- sequence accessor (set)*/ @@ -705,9 +590,6 @@ static int Matrix_ass_item(MatrixObject * self, int i, PyObject * ob) float vec[4]; PyObject *m, *f; - if(!BaseMath_ReadCallback(self)) - return -1; - if(i >= self->rowSize || i < 0){ PyErr_SetString(PyExc_TypeError, "matrix[attribute] = x: bad row\n"); return -1; @@ -741,8 +623,6 @@ static int Matrix_ass_item(MatrixObject * self, int i, PyObject * ob) for(y = 0; y < size; y++){ self->matrix[i][y] = vec[y]; } - - BaseMath_WriteCallback(self); return 0; }else{ PyErr_SetString(PyExc_TypeError, "matrix[attribute] = x: expects a sequence of column size\n"); @@ -756,9 +636,6 @@ static PyObject *Matrix_slice(MatrixObject * self, int begin, int end) PyObject *list = NULL; int count; - - if(!BaseMath_ReadCallback(self)) - return NULL; CLAMP(begin, 0, self->rowSize); CLAMP(end, 0, self->rowSize); @@ -767,8 +644,7 @@ static PyObject *Matrix_slice(MatrixObject * self, int begin, int end) list = PyList_New(end - begin); for(count = begin; count < end; count++) { PyList_SetItem(list, count - begin, - newVectorObject_cb((PyObject *)self, self->colSize, mathutils_matrix_vector_cb_index, count)); - + newVectorObject(self->matrix[count], self->colSize, Py_WRAP)); } return list; @@ -783,9 +659,6 @@ static int Matrix_ass_slice(MatrixObject * self, int begin, int end, PyObject *subseq; PyObject *m; - if(!BaseMath_ReadCallback(self)) - return -1; - CLAMP(begin, 0, self->rowSize); CLAMP(end, 0, self->rowSize); begin = MIN2(begin,end); @@ -843,8 +716,6 @@ static int Matrix_ass_slice(MatrixObject * self, int begin, int end, for(x = 0; x < (size * sub_size); x++){ self->matrix[begin + (int)floor(x / self->colSize)][x % self->colSize] = mat[x]; } - - BaseMath_WriteCallback(self); return 0; }else{ PyErr_SetString(PyExc_TypeError, "matrix[begin:end] = []: illegal argument type for built-in operation\n"); @@ -867,10 +738,6 @@ static PyObject *Matrix_add(PyObject * m1, PyObject * m2) PyErr_SetString(PyExc_AttributeError, "Matrix addition: arguments not valid for this operation...."); return NULL; } - - if(!BaseMath_ReadCallback(mat1) || !BaseMath_ReadCallback(mat2)) - return NULL; - if(mat1->rowSize != mat2->rowSize || mat1->colSize != mat2->colSize){ PyErr_SetString(PyExc_AttributeError, "Matrix addition: matrices must have the same dimensions for this operation"); return NULL; @@ -900,10 +767,6 @@ static PyObject *Matrix_sub(PyObject * m1, PyObject * m2) PyErr_SetString(PyExc_AttributeError, "Matrix addition: arguments not valid for this operation...."); return NULL; } - - if(!BaseMath_ReadCallback(mat1) || !BaseMath_ReadCallback(mat2)) - return NULL; - if(mat1->rowSize != mat2->rowSize || mat1->colSize != mat2->colSize){ PyErr_SetString(PyExc_AttributeError, "Matrix addition: matrices must have the same dimensions for this operation"); return NULL; @@ -928,16 +791,8 @@ static PyObject *Matrix_mul(PyObject * m1, PyObject * m2) double dot = 0.0f; MatrixObject *mat1 = NULL, *mat2 = NULL; - if(MatrixObject_Check(m1)) { - mat1 = (MatrixObject*)m1; - if(!BaseMath_ReadCallback(mat1)) - return NULL; - } - if(MatrixObject_Check(m2)) { - mat2 = (MatrixObject*)m2; - if(!BaseMath_ReadCallback(mat2)) - return NULL; - } + if(MatrixObject_Check(m1)) mat1 = (MatrixObject*)m1; + if(MatrixObject_Check(m2)) mat2 = (MatrixObject*)m2; if(mat1 && mat2) { /*MATRIX * MATRIX*/ if(mat1->colSize != mat2->rowSize){ @@ -974,7 +829,7 @@ static PyObject *Matrix_mul(PyObject * m1, PyObject * m2) else /* if(mat1) { */ { if(VectorObject_Check(m2)) { /* MATRIX*VECTOR */ - return column_vector_multiplication(mat1, (VectorObject *)m2); /* vector update done inside the function */ + return column_vector_multiplication(mat1, (VectorObject *)m2); } else { scalar= PyFloat_AsDouble(m2); @@ -996,9 +851,6 @@ static PyObject *Matrix_mul(PyObject * m1, PyObject * m2) } static PyObject* Matrix_inv(MatrixObject *self) { - if(!BaseMath_ReadCallback(self)) - return NULL; - return Matrix_Invert(self); } @@ -1012,46 +864,6 @@ static PySequenceMethods Matrix_SeqMethods = { (ssizeobjargproc) Matrix_ass_item, /* sq_ass_item */ (ssizessizeobjargproc) Matrix_ass_slice, /* sq_ass_slice */ }; - - -#if (PY_VERSION_HEX >= 0x03000000) -static PyNumberMethods Matrix_NumMethods = { - (binaryfunc) Matrix_add, /*nb_add*/ - (binaryfunc) Matrix_sub, /*nb_subtract*/ - (binaryfunc) Matrix_mul, /*nb_multiply*/ - 0, /*nb_remainder*/ - 0, /*nb_divmod*/ - 0, /*nb_power*/ - (unaryfunc) 0, /*nb_negative*/ - (unaryfunc) 0, /*tp_positive*/ - (unaryfunc) 0, /*tp_absolute*/ - (inquiry) 0, /*tp_bool*/ - (unaryfunc) Matrix_inv, /*nb_invert*/ - 0, /*nb_lshift*/ - (binaryfunc)0, /*nb_rshift*/ - 0, /*nb_and*/ - 0, /*nb_xor*/ - 0, /*nb_or*/ - 0, /*nb_int*/ - 0, /*nb_reserved*/ - 0, /*nb_float*/ - 0, /* nb_inplace_add */ - 0, /* nb_inplace_subtract */ - 0, /* nb_inplace_multiply */ - 0, /* nb_inplace_remainder */ - 0, /* nb_inplace_power */ - 0, /* nb_inplace_lshift */ - 0, /* nb_inplace_rshift */ - 0, /* nb_inplace_and */ - 0, /* nb_inplace_xor */ - 0, /* nb_inplace_or */ - 0, /* nb_floor_divide */ - 0, /* nb_true_divide */ - 0, /* nb_inplace_floor_divide */ - 0, /* nb_inplace_true_divide */ - 0, /* nb_index */ -}; -#else static PyNumberMethods Matrix_NumMethods = { (binaryfunc) Matrix_add, /* __add__ */ (binaryfunc) Matrix_sub, /* __sub__ */ @@ -1077,7 +889,6 @@ static PyNumberMethods Matrix_NumMethods = { (unaryfunc) 0, /* __oct__ */ (unaryfunc) 0, /* __hex__ */ }; -#endif static PyObject *Matrix_getRowSize( MatrixObject * self, void *type ) { @@ -1089,15 +900,21 @@ static PyObject *Matrix_getColSize( MatrixObject * self, void *type ) return PyLong_FromLong((long) self->colSize); } +static PyObject *Matrix_getWrapped( MatrixObject * self, void *type ) +{ + if (self->wrapped == Py_WRAP) + Py_RETURN_TRUE; + else + Py_RETURN_FALSE; +} + /*****************************************************************************/ /* Python attributes get/set structure: */ /*****************************************************************************/ static PyGetSetDef Matrix_getseters[] = { {"rowSize", (getter)Matrix_getRowSize, (setter)NULL, "", NULL}, {"colSize", (getter)Matrix_getColSize, (setter)NULL, "", NULL}, - {"wrapped", (getter)BaseMathObject_getWrapped, (setter)NULL, "", NULL}, - {"__owner__",(getter)BaseMathObject_getOwner, (setter)NULL, "", - NULL}, + {"wrapped", (getter)Matrix_getWrapped, (setter)NULL, "", NULL}, {NULL,NULL,NULL,NULL,NULL} /* Sentinel */ }; @@ -1113,7 +930,7 @@ PyTypeObject matrix_Type = { "matrix", /*tp_name*/ sizeof(MatrixObject), /*tp_basicsize*/ 0, /*tp_itemsize*/ - (destructor)BaseMathObject_dealloc, /*tp_dealloc*/ + (destructor)Matrix_dealloc, /*tp_dealloc*/ 0, /*tp_print*/ 0, /*tp_getattr*/ 0, /*tp_setattr*/ @@ -1167,7 +984,7 @@ self->matrix self->contiguous_ptr (reference to data.xxx) [4] [5] .... -self->matrix[1][1] = self->contigPtr[4] */ +self->matrix[1][1] = self->contiguous_ptr[4] = self->data.xxx_data[4]*/ /*pass Py_WRAP - if vector is a WRAPPER for data allocated by BLENDER (i.e. it was allocated elsewhere by MEM_mallocN()) @@ -1185,15 +1002,14 @@ PyObject *newMatrixObject(float *mat, int rowSize, int colSize, int type) } self = PyObject_NEW(MatrixObject, &matrix_Type); + self->data.blend_data = NULL; + self->data.py_data = NULL; self->rowSize = rowSize; self->colSize = colSize; - - /* init callbacks as NULL */ - self->cb_user= NULL; - self->cb_type= self->cb_subtype= 0; if(type == Py_WRAP){ - self->contigPtr = mat; + self->data.blend_data = mat; + self->contigPtr = self->data.blend_data; /*create pointer array*/ self->matrix = PyMem_Malloc(rowSize * sizeof(float *)); if(self->matrix == NULL) { /*allocation failure*/ @@ -1206,15 +1022,16 @@ PyObject *newMatrixObject(float *mat, int rowSize, int colSize, int type) } self->wrapped = Py_WRAP; }else if (type == Py_NEW){ - self->contigPtr = PyMem_Malloc(rowSize * colSize * sizeof(float)); - if(self->contigPtr == NULL) { /*allocation failure*/ + self->data.py_data = PyMem_Malloc(rowSize * colSize * sizeof(float)); + if(self->data.py_data == NULL) { /*allocation failure*/ PyErr_SetString( PyExc_MemoryError, "matrix(): problem allocating pointer space\n"); return NULL; } + self->contigPtr = self->data.py_data; /*create pointer array*/ self->matrix = PyMem_Malloc(rowSize * sizeof(float *)); if(self->matrix == NULL) { /*allocation failure*/ - PyMem_Free(self->contigPtr); + PyMem_Free(self->data.py_data); PyErr_SetString( PyExc_MemoryError, "matrix(): problem allocating pointer space"); return NULL; } @@ -1239,53 +1056,3 @@ PyObject *newMatrixObject(float *mat, int rowSize, int colSize, int type) } return (PyObject *) self; } - -PyObject *newMatrixObject_cb(PyObject *cb_user, int rowSize, int colSize, int cb_type, int cb_subtype) -{ - MatrixObject *self= (MatrixObject *)newMatrixObject(NULL, rowSize, colSize, Py_NEW); - if(self) { - Py_INCREF(cb_user); - self->cb_user= cb_user; - self->cb_type= (unsigned char)cb_type; - self->cb_subtype= (unsigned char)cb_subtype; - } - return (PyObject *) self; -} - -//----------------column_vector_multiplication (internal)--------- -//COLUMN VECTOR Multiplication (Matrix X Vector) -// [1][2][3] [a] -// [4][5][6] * [b] -// [7][8][9] [c] -//vector/matrix multiplication IS NOT COMMUTATIVE!!!! -static PyObject *column_vector_multiplication(MatrixObject * mat, VectorObject* vec) -{ - float vecNew[4], vecCopy[4]; - double dot = 0.0f; - int x, y, z = 0; - - if(!BaseMath_ReadCallback(mat) || !BaseMath_ReadCallback(vec)) - return NULL; - - if(mat->rowSize != vec->size){ - if(mat->rowSize == 4 && vec->size != 3){ - PyErr_SetString(PyExc_AttributeError, "matrix * vector: matrix row size and vector size must be the same"); - return NULL; - }else{ - vecCopy[3] = 1.0f; - } - } - - for(x = 0; x < vec->size; x++){ - vecCopy[x] = vec->vec[x]; - } - - for(x = 0; x < mat->rowSize; x++) { - for(y = 0; y < mat->colSize; y++) { - dot += mat->matrix[x][y] * vecCopy[y]; - } - vecNew[z++] = (float)dot; - dot = 0.0f; - } - return newVectorObject(vecNew, vec->size, Py_NEW); -} diff --git a/source/blender/python/generic/matrix.h b/source/blender/python/generic/matrix.h index 4b073668969..ef82263fe00 100644 --- a/source/blender/python/generic/matrix.h +++ b/source/blender/python/generic/matrix.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: matrix.h 20248 2009-05-18 04:11:54Z campbellbarton $ * ***** BEGIN GPL LICENSE BLOCK ***** * * This program is free software; you can redistribute it and/or @@ -37,19 +37,17 @@ extern PyTypeObject matrix_Type; #define MatrixObject_Check(v) ((v)->ob_type == &matrix_Type) typedef float **ptRow; -typedef struct _Matrix { /* keep aligned with BaseMathObject in Mathutils.h */ - PyObject_VAR_HEAD - float *contigPtr; /*1D array of data (alias)*/ - PyObject *cb_user; /* if this vector references another object, otherwise NULL, *Note* this owns its reference */ - unsigned char cb_type; /* which user funcs do we adhere to, RNA, GameObject, etc */ - unsigned char cb_subtype; /* subtype: location, rotation... to avoid defining many new functions for every attribute of the same type */ - unsigned char wrapped; /*is wrapped data?*/ - /* end BaseMathObject */ - - unsigned char rowSize; - unsigned int colSize; - ptRow matrix; /*ptr to the contigPtr (accessor)*/ - +typedef struct _Matrix { + PyObject_VAR_HEAD + struct{ + float *py_data; /*python managed*/ + float *blend_data; /*blender managed*/ + }data; + ptRow matrix; /*ptr to the contigPtr (accessor)*/ + float *contigPtr; /*1D array of data (alias)*/ + int rowSize; + int colSize; + int wrapped; /*is wrapped data?*/ } MatrixObject; /*struct data contains a pointer to the actual data that the @@ -59,9 +57,5 @@ blender (stored in blend_data). This is an either/or struct not both*/ /*prototypes*/ PyObject *newMatrixObject(float *mat, int rowSize, int colSize, int type); -PyObject *newMatrixObject_cb(PyObject *user, int rowSize, int colSize, int cb_type, int cb_subtype); - -extern int mathutils_matrix_vector_cb_index; -extern struct Mathutils_Callback mathutils_matrix_vector_cb; #endif /* EXPP_matrix_H */ diff --git a/source/blender/python/generic/quat.c b/source/blender/python/generic/quat.c index 7cd3cf738dd..4ad5d07b3b8 100644 --- a/source/blender/python/generic/quat.c +++ b/source/blender/python/generic/quat.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: quat.c 20332 2009-05-22 03:22:56Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -75,10 +75,10 @@ static struct PyMethodDef Quaternion_methods[] = { //----------------------------------Mathutils.Quaternion() -------------- static PyObject *Quaternion_new(PyTypeObject *type, PyObject *args, PyObject *kwds) { - PyObject *listObject = NULL, *n, *q; + PyObject *listObject = NULL, *n, *q, *f; int size, i; - float quat[4]; - double angle = 0.0f; + float quat[4], scalar; + double norm = 0.0f, angle = 0.0f; size = PyTuple_GET_SIZE(args); if (size == 1 || size == 2) { //seq? @@ -151,21 +151,29 @@ static PyObject *Quaternion_new(PyTypeObject *type, PyObject *args, PyObject *kw return NULL; } - quat[i] = PyFloat_AsDouble(q); - Py_DECREF(q); - - if (quat[i]==-1 && PyErr_Occurred()) { + scalar = PyFloat_AsDouble(q); + if (scalar==-1 && PyErr_Occurred()) { + Py_DECREF(q); PyErr_SetString(PyExc_TypeError, "Mathutils.Quaternion(): 4d numeric sequence expected or 3d vector and number\n"); return NULL; } - } - if(size == 3) //calculate the quat based on axis/angle -#ifdef USE_MATHUTILS_DEG - AxisAngleToQuat(quat, quat, angle * (Py_PI / 180)); -#else - AxisAngleToQuat(quat, quat, angle); -#endif + quat[i] = scalar; + Py_DECREF(f); + Py_DECREF(q); + } + if(size == 3){ //calculate the quat based on axis/angle + norm = sqrt(quat[0] * quat[0] + quat[1] * quat[1] + quat[2] * quat[2]); + quat[0] /= (float)norm; + quat[1] /= (float)norm; + quat[2] /= (float)norm; + + angle = angle * (Py_PI / 180); + quat[3] =(float) (sin(angle/ 2.0f)) * quat[2]; + quat[2] =(float) (sin(angle/ 2.0f)) * quat[1]; + quat[1] =(float) (sin(angle/ 2.0f)) * quat[0]; + quat[0] =(float) (cos(angle/ 2.0f)); + } return newQuaternionObject(quat, Py_NEW); } @@ -182,47 +190,33 @@ static PyObject *Quaternion_ToEuler(QuaternionObject * self, PyObject *args) if(!PyArg_ParseTuple(args, "|O!:toEuler", &euler_Type, &eul_compat)) return NULL; - if(!BaseMath_ReadCallback(self)) - return NULL; - if(eul_compat) { float mat[3][3], eul_compatf[3]; - if(!BaseMath_ReadCallback(eul_compat)) - return NULL; - - QuatToMat3(self->quat, mat); - -#ifdef USE_MATHUTILS_DEG for(x = 0; x < 3; x++) { eul_compatf[x] = eul_compat->eul[x] * ((float)Py_PI / 180); } + + QuatToMat3(self->quat, mat); Mat3ToCompatibleEul(mat, eul, eul_compatf); -#else - Mat3ToCompatibleEul(mat, eul, eul_compat->eul); -#endif } else { QuatToEul(self->quat, eul); } -#ifdef USE_MATHUTILS_DEG + for(x = 0; x < 3; x++) { eul[x] *= (180 / (float)Py_PI); } -#endif return newEulerObject(eul, Py_NEW); } //----------------------------Quaternion.toMatrix()------------------ //return the quat as a matrix static PyObject *Quaternion_ToMatrix(QuaternionObject * self) { - float mat[9]; /* all values are set */ - - if(!BaseMath_ReadCallback(self)) - return NULL; - + float mat[9] = {0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f}; QuatToMat3(self->quat, (float (*)[3]) mat); + return newMatrixObject(mat, 3, 3, Py_NEW); } @@ -237,9 +231,6 @@ static PyObject *Quaternion_Cross(QuaternionObject * self, QuaternionObject * va return NULL; } - if(!BaseMath_ReadCallback(self) || !BaseMath_ReadCallback(value)) - return NULL; - QuatMul(quat, self->quat, value->quat); return newQuaternionObject(quat, Py_NEW); } @@ -248,27 +239,25 @@ static PyObject *Quaternion_Cross(QuaternionObject * self, QuaternionObject * va //return the dot quat static PyObject *Quaternion_Dot(QuaternionObject * self, QuaternionObject * value) { + int x; + double dot = 0.0; + if (!QuaternionObject_Check(value)) { PyErr_SetString( PyExc_TypeError, "quat.dot(value): expected a quaternion argument" ); return NULL; } - - if(!BaseMath_ReadCallback(self) || !BaseMath_ReadCallback(value)) - return NULL; - - return PyFloat_FromDouble(QuatDot(self->quat, value->quat)); + + for(x = 0; x < 4; x++) { + dot += self->quat[x] * value->quat[x]; + } + return PyFloat_FromDouble(dot); } //----------------------------Quaternion.normalize()---------------- //normalize the axis of rotation of [theta,vector] static PyObject *Quaternion_Normalize(QuaternionObject * self) { - if(!BaseMath_ReadCallback(self)) - return NULL; - NormalQuat(self->quat); - - BaseMath_WriteCallback(self); Py_INCREF(self); return (PyObject*)self; } @@ -276,12 +265,20 @@ static PyObject *Quaternion_Normalize(QuaternionObject * self) //invert the quat static PyObject *Quaternion_Inverse(QuaternionObject * self) { - if(!BaseMath_ReadCallback(self)) - return NULL; + double mag = 0.0f; + int x; - QuatInv(self->quat); + for(x = 1; x < 4; x++) { + self->quat[x] = -self->quat[x]; + } + for(x = 0; x < 4; x++) { + mag += (self->quat[x] * self->quat[x]); + } + mag = sqrt(mag); + for(x = 0; x < 4; x++) { + self->quat[x] /= (float)(mag * mag); + } - BaseMath_WriteCallback(self); Py_INCREF(self); return (PyObject*)self; } @@ -289,12 +286,11 @@ static PyObject *Quaternion_Inverse(QuaternionObject * self) //generate the identity quaternion static PyObject *Quaternion_Identity(QuaternionObject * self) { - if(!BaseMath_ReadCallback(self)) - return NULL; - - QuatOne(self->quat); + self->quat[0] = 1.0; + self->quat[1] = 0.0; + self->quat[2] = 0.0; + self->quat[3] = 0.0; - BaseMath_WriteCallback(self); Py_INCREF(self); return (PyObject*)self; } @@ -302,12 +298,10 @@ static PyObject *Quaternion_Identity(QuaternionObject * self) //negate the quat static PyObject *Quaternion_Negate(QuaternionObject * self) { - if(!BaseMath_ReadCallback(self)) - return NULL; - - QuatMulf(self->quat, -1.0f); - - BaseMath_WriteCallback(self); + int x; + for(x = 0; x < 4; x++) { + self->quat[x] = -self->quat[x]; + } Py_INCREF(self); return (PyObject*)self; } @@ -315,12 +309,10 @@ static PyObject *Quaternion_Negate(QuaternionObject * self) //negate the vector part static PyObject *Quaternion_Conjugate(QuaternionObject * self) { - if(!BaseMath_ReadCallback(self)) - return NULL; - - QuatConj(self->quat); - - BaseMath_WriteCallback(self); + int x; + for(x = 1; x < 4; x++) { + self->quat[x] = -self->quat[x]; + } Py_INCREF(self); return (PyObject*)self; } @@ -328,21 +320,25 @@ static PyObject *Quaternion_Conjugate(QuaternionObject * self) //return a copy of the quat static PyObject *Quaternion_copy(QuaternionObject * self) { - if(!BaseMath_ReadCallback(self)) - return NULL; - return newQuaternionObject(self->quat, Py_NEW); } +//----------------------------dealloc()(internal) ------------------ +//free the py_object +static void Quaternion_dealloc(QuaternionObject * self) +{ + //only free py_data + if(self->data.py_data){ + PyMem_Free(self->data.py_data); + } + PyObject_DEL(self); +} + //----------------------------print object (internal)-------------- //print the object to screen static PyObject *Quaternion_repr(QuaternionObject * self) { char str[64]; - - if(!BaseMath_ReadCallback(self)) - return NULL; - sprintf(str, "[%.6f, %.6f, %.6f, %.6f](quaternion)", self->quat[0], self->quat[1], self->quat[2], self->quat[3]); return PyUnicode_FromString(str); } @@ -353,24 +349,15 @@ static PyObject* Quaternion_richcmpr(PyObject *objectA, PyObject *objectB, int c QuaternionObject *quatA = NULL, *quatB = NULL; int result = 0; - if(QuaternionObject_Check(objectA)) { - quatA = (QuaternionObject*)objectA; - if(!BaseMath_ReadCallback(quatA)) - return NULL; - } - if(QuaternionObject_Check(objectB)) { - quatB = (QuaternionObject*)objectB; - if(!BaseMath_ReadCallback(quatB)) - return NULL; - } - - if (!quatA || !quatB){ + if (!QuaternionObject_Check(objectA) || !QuaternionObject_Check(objectB)){ if (comparison_type == Py_NE){ Py_RETURN_TRUE; }else{ Py_RETURN_FALSE; } } + quatA = (QuaternionObject*)objectA; + quatB = (QuaternionObject*)objectB; switch (comparison_type){ case Py_EQ: @@ -407,16 +394,10 @@ static int Quaternion_len(QuaternionObject * self) //sequence accessor (get) static PyObject *Quaternion_item(QuaternionObject * self, int i) { - if(i<0) i= 4-i; - if(i < 0 || i >= 4) { PyErr_SetString(PyExc_IndexError, "quaternion[attribute]: array index out of range\n"); return NULL; } - - if(!BaseMath_ReadIndexCallback(self, i)) - return NULL; - return PyFloat_FromDouble(self->quat[i]); } @@ -424,23 +405,21 @@ static PyObject *Quaternion_item(QuaternionObject * self, int i) //sequence accessor (set) static int Quaternion_ass_item(QuaternionObject * self, int i, PyObject * ob) { - float scalar= (float)PyFloat_AsDouble(ob); - if(scalar==-1.0f && PyErr_Occurred()) { /* parsed item not a number */ - PyErr_SetString(PyExc_TypeError, "quaternion[index] = x: index argument not a number\n"); + PyObject *f = NULL; + + f = PyNumber_Float(ob); + if(f == NULL) { // parsed item not a number + PyErr_SetString(PyExc_TypeError, "quaternion[attribute] = x: argument not a number\n"); return -1; } - if(i<0) i= 4-i; - if(i < 0 || i >= 4){ + Py_DECREF(f); PyErr_SetString(PyExc_IndexError, "quaternion[attribute] = x: array assignment index out of range\n"); return -1; } - self->quat[i] = scalar; - - if(!BaseMath_WriteIndexCallback(self, i)) - return -1; - + self->quat[i] = (float)PyFloat_AS_DOUBLE(f); + Py_DECREF(f); return 0; } //----------------------------object[z:y]------------------------ @@ -450,9 +429,6 @@ static PyObject *Quaternion_slice(QuaternionObject * self, int begin, int end) PyObject *list = NULL; int count; - if(!BaseMath_ReadCallback(self)) - return NULL; - CLAMP(begin, 0, 4); if (end<0) end= 5+end; CLAMP(end, 0, 4); @@ -468,14 +444,12 @@ static PyObject *Quaternion_slice(QuaternionObject * self, int begin, int end) } //----------------------------object[z:y]------------------------ //sequence slice (set) -static int Quaternion_ass_slice(QuaternionObject * self, int begin, int end, PyObject * seq) +static int Quaternion_ass_slice(QuaternionObject * self, int begin, int end, + PyObject * seq) { int i, y, size = 0; float quat[4]; - PyObject *q; - - if(!BaseMath_ReadCallback(self)) - return -1; + PyObject *q, *f; CLAMP(begin, 0, 4); if (end<0) end= 5+end; @@ -495,19 +469,21 @@ static int Quaternion_ass_slice(QuaternionObject * self, int begin, int end, PyO return -1; } - quat[i]= (float)PyFloat_AsDouble(q); - Py_DECREF(q); - - if(quat[i]==-1.0f && PyErr_Occurred()) { /* parsed item not a number */ + f = PyNumber_Float(q); + if(f == NULL) { // parsed item not a number + Py_DECREF(q); PyErr_SetString(PyExc_TypeError, "quaternion[begin:end] = []: sequence argument not a number\n"); return -1; } + + quat[i] = (float)PyFloat_AS_DOUBLE(f); + Py_DECREF(f); + Py_DECREF(q); } //parsed well - now set in vector - for(y = 0; y < size; y++) + for(y = 0; y < size; y++){ self->quat[begin + y] = quat[y]; - - BaseMath_WriteCallback(self); + } return 0; } //------------------------NUMERIC PROTOCOLS---------------------- @@ -515,6 +491,7 @@ static int Quaternion_ass_slice(QuaternionObject * self, int begin, int end, PyO //addition static PyObject *Quaternion_add(PyObject * q1, PyObject * q2) { + int x; float quat[4]; QuaternionObject *quat1 = NULL, *quat2 = NULL; @@ -522,13 +499,14 @@ static PyObject *Quaternion_add(PyObject * q1, PyObject * q2) PyErr_SetString(PyExc_AttributeError, "Quaternion addition: arguments not valid for this operation....\n"); return NULL; } + quat1 = (QuaternionObject*)q1; quat2 = (QuaternionObject*)q2; - if(!BaseMath_ReadCallback(quat1) || !BaseMath_ReadCallback(quat2)) - return NULL; + for(x = 0; x < 4; x++) { + quat[x] = quat1->quat[x] + quat2->quat[x]; + } - QuatAdd(quat, quat1->quat, quat2->quat, 1.0f); return newQuaternionObject(quat, Py_NEW); } //------------------------obj - obj------------------------------ @@ -547,9 +525,6 @@ static PyObject *Quaternion_sub(PyObject * q1, PyObject * q2) quat1 = (QuaternionObject*)q1; quat2 = (QuaternionObject*)q2; - if(!BaseMath_ReadCallback(quat1) || !BaseMath_ReadCallback(quat2)) - return NULL; - for(x = 0; x < 4; x++) { quat[x] = quat1->quat[x] - quat2->quat[x]; } @@ -560,31 +535,29 @@ static PyObject *Quaternion_sub(PyObject * q1, PyObject * q2) //mulplication static PyObject *Quaternion_mul(PyObject * q1, PyObject * q2) { + int x; float quat[4], scalar; + double dot = 0.0f; QuaternionObject *quat1 = NULL, *quat2 = NULL; VectorObject *vec = NULL; - if(QuaternionObject_Check(q1)) { - quat1 = (QuaternionObject*)q1; - if(!BaseMath_ReadCallback(quat1)) - return NULL; - } - if(QuaternionObject_Check(q2)) { - quat2 = (QuaternionObject*)q2; - if(!BaseMath_ReadCallback(quat2)) - return NULL; - } + quat1 = (QuaternionObject*)q1; + quat2 = (QuaternionObject*)q2; - if(quat1 && quat2) { /* QUAT*QUAT (dot product) */ - return PyFloat_FromDouble(QuatDot(quat1->quat, quat2->quat)); + if(QuaternionObject_Check(q1) && QuaternionObject_Check(q2)) { /* QUAT*QUAT (dot product) */ + for(x = 0; x < 4; x++) { + dot += quat1->quat[x] * quat1->quat[x]; + } + return PyFloat_FromDouble(dot); } /* the only case this can happen (for a supported type is "FLOAT*QUAT" ) */ if(!QuaternionObject_Check(q1)) { scalar= PyFloat_AsDouble(q1); if ((scalar == -1.0 && PyErr_Occurred())==0) { /* FLOAT*QUAT */ - QUATCOPY(quat, quat2->quat); - QuatMulf(quat, scalar); + for(x = 0; x < 4; x++) { + quat[x] = quat2->quat[x] * scalar; + } return newQuaternionObject(quat, Py_NEW); } PyErr_SetString(PyExc_TypeError, "Quaternion multiplication: val * quat, val is not an acceptable type"); @@ -597,13 +570,14 @@ static PyObject *Quaternion_mul(PyObject * q1, PyObject * q2) PyErr_SetString(PyExc_TypeError, "Quaternion multiplication: only 3D vector rotations currently supported\n"); return NULL; } - return quat_rotation((PyObject*)quat1, (PyObject*)vec); /* vector updating done inside the func */ + return quat_rotation((PyObject*)quat1, (PyObject*)vec); } scalar= PyFloat_AsDouble(q2); if ((scalar == -1.0 && PyErr_Occurred())==0) { /* QUAT*FLOAT */ - QUATCOPY(quat, quat1->quat); - QuatMulf(quat, scalar); + for(x = 0; x < 4; x++) { + quat[x] = quat1->quat[x] * scalar; + } return newQuaternionObject(quat, Py_NEW); } } @@ -622,45 +596,6 @@ static PySequenceMethods Quaternion_SeqMethods = { (ssizeobjargproc) Quaternion_ass_item, /* sq_ass_item */ (ssizessizeobjargproc) Quaternion_ass_slice, /* sq_ass_slice */ }; - -#if (PY_VERSION_HEX >= 0x03000000) -static PyNumberMethods Quaternion_NumMethods = { - (binaryfunc) Quaternion_add, /*nb_add*/ - (binaryfunc) Quaternion_sub, /*nb_subtract*/ - (binaryfunc) Quaternion_mul, /*nb_multiply*/ - 0, /*nb_remainder*/ - 0, /*nb_divmod*/ - 0, /*nb_power*/ - (unaryfunc) 0, /*nb_negative*/ - (unaryfunc) 0, /*tp_positive*/ - (unaryfunc) 0, /*tp_absolute*/ - (inquiry) 0, /*tp_bool*/ - (unaryfunc) 0, /*nb_invert*/ - 0, /*nb_lshift*/ - (binaryfunc)0, /*nb_rshift*/ - 0, /*nb_and*/ - 0, /*nb_xor*/ - 0, /*nb_or*/ - 0, /*nb_int*/ - 0, /*nb_reserved*/ - 0, /*nb_float*/ - 0, /* nb_inplace_add */ - 0, /* nb_inplace_subtract */ - 0, /* nb_inplace_multiply */ - 0, /* nb_inplace_remainder */ - 0, /* nb_inplace_power */ - 0, /* nb_inplace_lshift */ - 0, /* nb_inplace_rshift */ - 0, /* nb_inplace_and */ - 0, /* nb_inplace_xor */ - 0, /* nb_inplace_or */ - 0, /* nb_floor_divide */ - 0, /* nb_true_divide */ - 0, /* nb_inplace_floor_divide */ - 0, /* nb_inplace_true_divide */ - 0, /* nb_index */ -}; -#else static PyNumberMethods Quaternion_NumMethods = { (binaryfunc) Quaternion_add, /* __add__ */ (binaryfunc) Quaternion_sub, /* __sub__ */ @@ -685,31 +620,76 @@ static PyNumberMethods Quaternion_NumMethods = { (unaryfunc) 0, /* __float__ */ (unaryfunc) 0, /* __oct__ */ (unaryfunc) 0, /* __hex__ */ + }; -#endif + static PyObject *Quaternion_getAxis( QuaternionObject * self, void *type ) { - return Quaternion_item(self, GET_INT_FROM_POINTER(type)); + switch( (long)type ) { + case 'W': + return PyFloat_FromDouble(self->quat[0]); + case 'X': + return PyFloat_FromDouble(self->quat[1]); + case 'Y': + return PyFloat_FromDouble(self->quat[2]); + case 'Z': + return PyFloat_FromDouble(self->quat[3]); + } + + PyErr_SetString(PyExc_SystemError, "corrupt quaternion, cannot get axis"); + return NULL; } static int Quaternion_setAxis( QuaternionObject * self, PyObject * value, void * type ) { - return Quaternion_ass_item(self, GET_INT_FROM_POINTER(type), value); + float param= (float)PyFloat_AsDouble( value ); + + if (param==-1 && PyErr_Occurred()) { + PyErr_SetString( PyExc_TypeError, "expected a number for the vector axis" ); + return -1; + } + switch( (long)type ) { + case 'W': + self->quat[0]= param; + break; + case 'X': + self->quat[1]= param; + break; + case 'Y': + self->quat[2]= param; + break; + case 'Z': + self->quat[3]= param; + break; + } + + return 0; +} + +static PyObject *Quaternion_getWrapped( QuaternionObject * self, void *type ) +{ + if (self->wrapped == Py_WRAP) + Py_RETURN_TRUE; + else + Py_RETURN_FALSE; } static PyObject *Quaternion_getMagnitude( QuaternionObject * self, void *type ) { - return PyFloat_FromDouble(sqrt(QuatDot(self->quat, self->quat))); + double mag = 0.0; + int i; + for(i = 0; i < 4; i++) { + mag += self->quat[i] * self->quat[i]; + } + return PyFloat_FromDouble(sqrt(mag)); } static PyObject *Quaternion_getAngle( QuaternionObject * self, void *type ) { double ang = self->quat[0]; ang = 2 * (saacos(ang)); -#ifdef USE_MATHUTILS_DEG ang *= (180 / Py_PI); -#endif return PyFloat_FromDouble(ang); } @@ -741,19 +721,19 @@ static PyGetSetDef Quaternion_getseters[] = { {"w", (getter)Quaternion_getAxis, (setter)Quaternion_setAxis, "Quaternion W value", - (void *)0}, + (void *)'W'}, {"x", (getter)Quaternion_getAxis, (setter)Quaternion_setAxis, "Quaternion X axis", - (void *)1}, + (void *)'X'}, {"y", (getter)Quaternion_getAxis, (setter)Quaternion_setAxis, "Quaternion Y axis", - (void *)2}, + (void *)'Y'}, {"z", (getter)Quaternion_getAxis, (setter)Quaternion_setAxis, "Quaternion Z axis", - (void *)3}, + (void *)'Z'}, {"magnitude", (getter)Quaternion_getMagnitude, (setter)NULL, "Size of the quaternion", @@ -767,14 +747,9 @@ static PyGetSetDef Quaternion_getseters[] = { "quaternion axis as a vector", NULL}, {"wrapped", - (getter)BaseMathObject_getWrapped, (setter)NULL, + (getter)Quaternion_getWrapped, (setter)NULL, "True when this wraps blenders internal data", NULL}, - {"__owner__", - (getter)BaseMathObject_getOwner, (setter)NULL, - "Read only owner for vectors that depend on another object", - NULL}, - {NULL,NULL,NULL,NULL,NULL} /* Sentinel */ }; @@ -791,7 +766,7 @@ PyTypeObject quaternion_Type = { "quaternion", //tp_name sizeof(QuaternionObject), //tp_basicsize 0, //tp_itemsize - (destructor)BaseMathObject_dealloc, //tp_dealloc + (destructor)Quaternion_dealloc, //tp_dealloc 0, //tp_print 0, //tp_getattr 0, //tp_setattr @@ -843,22 +818,26 @@ PyTypeObject quaternion_Type = { PyObject *newQuaternionObject(float *quat, int type) { QuaternionObject *self; + int x; self = PyObject_NEW(QuaternionObject, &quaternion_Type); - - /* init callbacks as NULL */ - self->cb_user= NULL; - self->cb_type= self->cb_subtype= 0; + self->data.blend_data = NULL; + self->data.py_data = NULL; if(type == Py_WRAP){ - self->quat = quat; + self->data.blend_data = quat; + self->quat = self->data.blend_data; self->wrapped = Py_WRAP; }else if (type == Py_NEW){ - self->quat = PyMem_Malloc(4 * sizeof(float)); + self->data.py_data = PyMem_Malloc(4 * sizeof(float)); + self->quat = self->data.py_data; if(!quat) { //new empty - QuatOne(self->quat); + Quaternion_Identity(self); + Py_DECREF(self); }else{ - QUATCOPY(self->quat, quat); + for(x = 0; x < 4; x++){ + self->quat[x] = quat[x]; + } } self->wrapped = Py_NEW; }else{ //bad type @@ -866,16 +845,3 @@ PyObject *newQuaternionObject(float *quat, int type) } return (PyObject *) self; } - -PyObject *newQuaternionObject_cb(PyObject *cb_user, int cb_type, int cb_subtype) -{ - QuaternionObject *self= (QuaternionObject *)newQuaternionObject(NULL, Py_NEW); - if(self) { - Py_INCREF(cb_user); - self->cb_user= cb_user; - self->cb_type= (unsigned char)cb_type; - self->cb_subtype= (unsigned char)cb_subtype; - } - - return (PyObject *)self; -} diff --git a/source/blender/python/generic/quat.h b/source/blender/python/generic/quat.h index 2e74b5fa7f9..cfb50e4dbe1 100644 --- a/source/blender/python/generic/quat.h +++ b/source/blender/python/generic/quat.h @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: quat.h 20332 2009-05-22 03:22:56Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -38,15 +38,14 @@ extern PyTypeObject quaternion_Type; #define QuaternionObject_Check(v) (Py_TYPE(v) == &quaternion_Type) -typedef struct { /* keep aligned with BaseMathObject in Mathutils.h */ +typedef struct { PyObject_VAR_HEAD - float *quat; /* 1D array of data (alias) */ - PyObject *cb_user; /* if this vector references another object, otherwise NULL, *Note* this owns its reference */ - unsigned char cb_type; /* which user funcs do we adhere to, RNA, GameObject, etc */ - unsigned char cb_subtype; /* subtype: location, rotation... to avoid defining many new functions for every attribute of the same type */ - unsigned char wrapped; /* wrapped data type? */ - /* end BaseMathObject */ - + struct{ + float *py_data; //python managed + float *blend_data; //blender managed + }data; + float *quat; //1D array of data (alias) + int wrapped; //is wrapped data? } QuaternionObject; /*struct data contains a pointer to the actual data that the @@ -56,6 +55,5 @@ blender (stored in blend_data). This is an either/or struct not both*/ //prototypes PyObject *newQuaternionObject( float *quat, int type ); -PyObject *newQuaternionObject_cb(PyObject *cb_user, int cb_type, int cb_subtype); #endif /* EXPP_quat_h */ diff --git a/source/blender/python/generic/vector.c b/source/blender/python/generic/vector.c index d8d4c33b6f8..562413c6967 100644 --- a/source/blender/python/generic/vector.c +++ b/source/blender/python/generic/vector.c @@ -1,5 +1,5 @@ /* - * $Id$ + * $Id: vector.c 20332 2009-05-22 03:22:56Z campbellbarton $ * ***** BEGIN GPL LICENSE BLOCK ***** * * This program is free software; you can redistribute it and/or @@ -39,8 +39,6 @@ #define SWIZZLE_VALID_AXIS 0x4 #define SWIZZLE_AXIS 0x3 -static PyObject *row_vector_multiplication(VectorObject* vec, MatrixObject * mat); /* utility func */ - /*-------------------------DOC STRINGS ---------------------------*/ static char Vector_Zero_doc[] = "() - set all values in the vector to 0"; static char Vector_Normalize_doc[] = "() - normalize the vector"; @@ -62,7 +60,7 @@ static PyObject *Vector_Resize2D( VectorObject * self ); static PyObject *Vector_Resize3D( VectorObject * self ); static PyObject *Vector_Resize4D( VectorObject * self ); static PyObject *Vector_ToTrackQuat( VectorObject * self, PyObject * args ); -static PyObject *Vector_Reflect( VectorObject *self, VectorObject *value ); +static PyObject *Vector_Reflect( VectorObject * self, PyObject * value ); static PyObject *Vector_Cross( VectorObject * self, VectorObject * value ); static PyObject *Vector_Dot( VectorObject * self, VectorObject * value ); static PyObject *Vector_copy( VectorObject * self ); @@ -72,8 +70,8 @@ static struct PyMethodDef Vector_methods[] = { {"normalize", (PyCFunction) Vector_Normalize, METH_NOARGS, Vector_Normalize_doc}, {"negate", (PyCFunction) Vector_Negate, METH_NOARGS, Vector_Negate_doc}, {"resize2D", (PyCFunction) Vector_Resize2D, METH_NOARGS, Vector_Resize2D_doc}, - {"resize3D", (PyCFunction) Vector_Resize3D, METH_NOARGS, Vector_Resize3D_doc}, - {"resize4D", (PyCFunction) Vector_Resize4D, METH_NOARGS, Vector_Resize4D_doc}, + {"resize3D", (PyCFunction) Vector_Resize3D, METH_NOARGS, Vector_Resize2D_doc}, + {"resize4D", (PyCFunction) Vector_Resize4D, METH_NOARGS, Vector_Resize2D_doc}, {"toTrackQuat", ( PyCFunction ) Vector_ToTrackQuat, METH_VARARGS, Vector_ToTrackQuat_doc}, {"reflect", ( PyCFunction ) Vector_Reflect, METH_O, Vector_Reflect_doc}, {"cross", ( PyCFunction ) Vector_Cross, METH_O, Vector_Dot_doc}, @@ -143,8 +141,6 @@ static PyObject *Vector_Zero(VectorObject * self) for(i = 0; i < self->size; i++) { self->vec[i] = 0.0f; } - - BaseMath_WriteCallback(self); Py_INCREF(self); return (PyObject*)self; } @@ -155,9 +151,6 @@ static PyObject *Vector_Normalize(VectorObject * self) int i; float norm = 0.0f; - if(!BaseMath_ReadCallback(self)) - return NULL; - for(i = 0; i < self->size; i++) { norm += self->vec[i] * self->vec[i]; } @@ -165,8 +158,6 @@ static PyObject *Vector_Normalize(VectorObject * self) for(i = 0; i < self->size; i++) { self->vec[i] /= norm; } - - BaseMath_WriteCallback(self); Py_INCREF(self); return (PyObject*)self; } @@ -180,11 +171,6 @@ static PyObject *Vector_Resize2D(VectorObject * self) PyErr_SetString(PyExc_TypeError, "vector.resize2d(): cannot resize wrapped data - only python vectors\n"); return NULL; } - if(self->cb_user) { - PyErr_SetString(PyExc_TypeError, "vector.resize4d(): cannot resize a vector that has an owner"); - return NULL; - } - self->vec = PyMem_Realloc(self->vec, (sizeof(float) * 2)); if(self->vec == NULL) { PyErr_SetString(PyExc_MemoryError, "vector.resize2d(): problem allocating pointer space\n\n"); @@ -203,11 +189,6 @@ static PyObject *Vector_Resize3D(VectorObject * self) PyErr_SetString(PyExc_TypeError, "vector.resize3d(): cannot resize wrapped data - only python vectors\n"); return NULL; } - if(self->cb_user) { - PyErr_SetString(PyExc_TypeError, "vector.resize4d(): cannot resize a vector that has an owner"); - return NULL; - } - self->vec = PyMem_Realloc(self->vec, (sizeof(float) * 3)); if(self->vec == NULL) { PyErr_SetString(PyExc_MemoryError, "vector.resize3d(): problem allocating pointer space\n\n"); @@ -229,11 +210,6 @@ static PyObject *Vector_Resize4D(VectorObject * self) PyErr_SetString(PyExc_TypeError, "vector.resize4d(): cannot resize wrapped data - only python vectors"); return NULL; } - if(self->cb_user) { - PyErr_SetString(PyExc_TypeError, "vector.resize4d(): cannot resize a vector that has an owner"); - return NULL; - } - self->vec = PyMem_Realloc(self->vec, (sizeof(float) * 4)); if(self->vec == NULL) { PyErr_SetString(PyExc_MemoryError, "vector.resize4d(): problem allocating pointer space\n\n"); @@ -265,9 +241,6 @@ static PyObject *Vector_ToTrackQuat( VectorObject * self, PyObject * args ) PyErr_SetString( PyExc_TypeError, "only for 3D vectors\n" ); return NULL; } - - if(!BaseMath_ReadCallback(self)) - return NULL; if (strack) { if (strlen(strack) == 2) { @@ -369,8 +342,9 @@ static PyObject *Vector_ToTrackQuat( VectorObject * self, PyObject * args ) return a reflected vector on the mirror normal ((2 * DotVecs(vec, mirror)) * mirror) - vec using arithb.c would be nice here */ -static PyObject *Vector_Reflect( VectorObject * self, VectorObject * value ) +static PyObject *Vector_Reflect( VectorObject * self, PyObject * value ) { + VectorObject *mirrvec; float mirror[3]; float vec[3]; float reflect[4] = {0.0f, 0.0f, 0.0f, 0.0f}; @@ -384,13 +358,11 @@ static PyObject *Vector_Reflect( VectorObject * self, VectorObject * value ) PyErr_SetString( PyExc_TypeError, "vec.reflect(value): expected a vector argument" ); return NULL; } + mirrvec = (VectorObject *)value; - if(!BaseMath_ReadCallback(self) || !BaseMath_ReadCallback(value)) - return NULL; - - mirror[0] = value->vec[0]; - mirror[1] = value->vec[1]; - if (value->size > 2) mirror[2] = value->vec[2]; + mirror[0] = mirrvec->vec[0]; + mirror[1] = mirrvec->vec[1]; + if (mirrvec->size > 2) mirror[2] = mirrvec->vec[2]; else mirror[2] = 0.0; /* normalize, whos idea was it not to use arithb.c? :-/ */ @@ -431,9 +403,6 @@ static PyObject *Vector_Cross( VectorObject * self, VectorObject * value ) return NULL; } - if(!BaseMath_ReadCallback(self) || !BaseMath_ReadCallback(value)) - return NULL; - vecCross = (VectorObject *)newVectorObject(NULL, 3, Py_NEW); Crossf(vecCross->vec, self->vec, value->vec); return (PyObject *)vecCross; @@ -454,9 +423,6 @@ static PyObject *Vector_Dot( VectorObject * self, VectorObject * value ) return NULL; } - if(!BaseMath_ReadCallback(self) || !BaseMath_ReadCallback(value)) - return NULL; - for(x = 0; x < self->size; x++) { dot += self->vec[x] * value->vec[x]; } @@ -467,12 +433,20 @@ static PyObject *Vector_Dot( VectorObject * self, VectorObject * value ) return a copy of the vector */ static PyObject *Vector_copy(VectorObject * self) { - if(!BaseMath_ReadCallback(self)) - return NULL; - return newVectorObject(self->vec, self->size, Py_NEW); } +/*----------------------------dealloc()(internal) ---------------- + free the py_object */ +static void Vector_dealloc(VectorObject * self) +{ + /* only free non wrapped */ + if(self->wrapped != Py_WRAP){ + PyMem_Free(self->vec); + } + PyObject_DEL(self); +} + /*----------------------------print object (internal)------------- print the object to screen */ static PyObject *Vector_repr(VectorObject * self) @@ -480,9 +454,6 @@ static PyObject *Vector_repr(VectorObject * self) int i; char buffer[48], str[1024]; - if(!BaseMath_ReadCallback(self)) - return NULL; - BLI_strncpy(str,"[",1024); for(i = 0; i < self->size; i++){ if(i < (self->size - 1)){ @@ -508,16 +479,11 @@ static int Vector_len(VectorObject * self) sequence accessor (get)*/ static PyObject *Vector_item(VectorObject * self, int i) { - if(i<0) i= self->size-i; - if(i < 0 || i >= self->size) { PyErr_SetString(PyExc_IndexError,"vector[index]: out of range\n"); return NULL; } - if(!BaseMath_ReadIndexCallback(self, i)) - return NULL; - return PyFloat_FromDouble(self->vec[i]); } @@ -531,16 +497,11 @@ static int Vector_ass_item(VectorObject * self, int i, PyObject * ob) return -1; } - if(i<0) i= self->size-i; - if(i < 0 || i >= self->size){ PyErr_SetString(PyExc_IndexError, "vector[index] = x: assignment index out of range\n"); return -1; } self->vec[i] = scalar; - - if(!BaseMath_WriteIndexCallback(self, i)) - return -1; return 0; } @@ -551,9 +512,6 @@ static PyObject *Vector_slice(VectorObject * self, int begin, int end) PyObject *list = NULL; int count; - if(!BaseMath_ReadCallback(self)) - return NULL; - CLAMP(begin, 0, self->size); if (end<0) end= self->size+end+1; CLAMP(end, 0, self->size); @@ -576,9 +534,6 @@ static int Vector_ass_slice(VectorObject * self, int begin, int end, float vec[4], scalar; PyObject *v; - if(!BaseMath_ReadCallback(self)) - return -1; - CLAMP(begin, 0, self->size); if (end<0) end= self->size+end+1; CLAMP(end, 0, self->size); @@ -611,10 +566,6 @@ static int Vector_ass_slice(VectorObject * self, int begin, int end, for(y = 0; y < size; y++){ self->vec[begin + y] = vec[y]; } - - if(!BaseMath_WriteCallback(self)) - return -1; - return 0; } /*------------------------NUMERIC PROTOCOLS---------------------- @@ -635,10 +586,6 @@ static PyObject *Vector_add(PyObject * v1, PyObject * v2) /* make sure v1 is always the vector */ if (vec1 && vec2 ) { - - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2)) - return NULL; - /*VECTOR + VECTOR*/ if(vec1->size != vec2->size) { PyErr_SetString(PyExc_AttributeError, "Vector addition: vectors must have the same dimensions for this operation\n"); @@ -670,10 +617,6 @@ static PyObject *Vector_iadd(PyObject * v1, PyObject * v2) /* make sure v1 is always the vector */ if (vec1 && vec2 ) { - - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2)) - return NULL; - /*VECTOR + VECTOR*/ if(vec1->size != vec2->size) { PyErr_SetString(PyExc_AttributeError, "Vector addition: vectors must have the same dimensions for this operation\n"); @@ -686,7 +629,6 @@ static PyObject *Vector_iadd(PyObject * v1, PyObject * v2) return v1; } - BaseMath_WriteCallback(vec1); PyErr_SetString(PyExc_AttributeError, "Vector addition: arguments not valid for this operation....\n"); return NULL; } @@ -706,9 +648,6 @@ static PyObject *Vector_sub(PyObject * v1, PyObject * v2) vec1 = (VectorObject*)v1; vec2 = (VectorObject*)v2; - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2)) - return NULL; - if(vec1->size != vec2->size) { PyErr_SetString(PyExc_AttributeError, "Vector subtraction: vectors must have the same dimensions for this operation\n"); return NULL; @@ -724,7 +663,7 @@ static PyObject *Vector_sub(PyObject * v1, PyObject * v2) subtraction*/ static PyObject *Vector_isub(PyObject * v1, PyObject * v2) { - int i; + int i, size; VectorObject *vec1 = NULL, *vec2 = NULL; if (!VectorObject_Check(v1) || !VectorObject_Check(v2)) { @@ -738,15 +677,12 @@ static PyObject *Vector_isub(PyObject * v1, PyObject * v2) PyErr_SetString(PyExc_AttributeError, "Vector subtraction: vectors must have the same dimensions for this operation\n"); return NULL; } - - if(!BaseMath_ReadCallback(vec1) || !BaseMath_ReadCallback(vec2)) - return NULL; + size = vec1->size; for(i = 0; i < vec1->size; i++) { vec1->vec[i] = vec1->vec[i] - vec2->vec[i]; } - BaseMath_WriteCallback(vec1); Py_INCREF( v1 ); return v1; } @@ -758,17 +694,11 @@ static PyObject *Vector_mul(PyObject * v1, PyObject * v2) VectorObject *vec1 = NULL, *vec2 = NULL; float scalar; - if VectorObject_Check(v1) { + if VectorObject_Check(v1) vec1= (VectorObject *)v1; - if(!BaseMath_ReadCallback(vec1)) - return NULL; - } - if VectorObject_Check(v2) { - vec2= (VectorObject *)v2; - if(!BaseMath_ReadCallback(vec2)) - return NULL; - } + if VectorObject_Check(v2) + vec2= (VectorObject *)v2; /* make sure v1 is always the vector */ if (vec1 && vec2 ) { @@ -797,8 +727,7 @@ static PyObject *Vector_mul(PyObject * v1, PyObject * v2) /* VEC * MATRIX */ return row_vector_multiplication(vec1, (MatrixObject*)v2); } else if (QuaternionObject_Check(v2)) { - QuaternionObject *quat = (QuaternionObject*)v2; /* quat_rotation validates */ - + QuaternionObject *quat = (QuaternionObject*)v2; if(vec1->size != 3) { PyErr_SetString(PyExc_TypeError, "Vector multiplication: only 3D vector rotations (with quats) currently supported\n"); return NULL; @@ -828,9 +757,6 @@ static PyObject *Vector_imul(PyObject * v1, PyObject * v2) int i; float scalar; - if(!BaseMath_ReadCallback(vec)) - return NULL; - /* only support vec*=float and vec*=mat vec*=vec result is a float so that wont work */ if (MatrixObject_Check(v2)) { @@ -838,9 +764,6 @@ static PyObject *Vector_imul(PyObject * v1, PyObject * v2) int x,y, size = vec->size; MatrixObject *mat= (MatrixObject*)v2; - if(!BaseMath_ReadCallback(mat)) - return NULL; - if(mat->colSize != size){ if(mat->rowSize == 4 && vec->size != 3){ PyErr_SetString(PyExc_AttributeError, "vector * matrix: matrix column size and the vector size must be the same"); @@ -864,21 +787,22 @@ static PyObject *Vector_imul(PyObject * v1, PyObject * v2) } vec->vec[i] = (float)dot; } + Py_INCREF( v1 ); + return v1; } else if (((scalar= PyFloat_AsDouble(v2)) == -1.0 && PyErr_Occurred())==0) { /* VEC*=FLOAT */ for(i = 0; i < vec->size; i++) { vec->vec[i] *= scalar; } - } - else { - PyErr_SetString(PyExc_TypeError, "Vector multiplication: arguments not acceptable for this operation\n"); - return NULL; + + Py_INCREF( v1 ); + return v1; + } - BaseMath_WriteCallback(vec); - Py_INCREF( v1 ); - return v1; + PyErr_SetString(PyExc_TypeError, "Vector multiplication: arguments not acceptable for this operation\n"); + return NULL; } /*------------------------obj / obj------------------------------ @@ -895,9 +819,6 @@ static PyObject *Vector_div(PyObject * v1, PyObject * v2) } vec1 = (VectorObject*)v1; /* vector */ - if(!BaseMath_ReadCallback(vec1)) - return NULL; - scalar = (float)PyFloat_AsDouble(v2); if(scalar== -1.0f && PyErr_Occurred()) { /* parsed item not a number */ PyErr_SetString(PyExc_TypeError, "Vector division: Vector must be divided by a float\n"); @@ -921,10 +842,14 @@ static PyObject *Vector_idiv(PyObject * v1, PyObject * v2) { int i; float scalar; - VectorObject *vec1 = (VectorObject*)v1; + VectorObject *vec1 = NULL; - if(!BaseMath_ReadCallback(vec1)) - return NULL; + /*if(!VectorObject_Check(v1)) { + PyErr_SetString(PyExc_TypeError, "Vector division: Vector must be divided by a float\n"); + return -1; + }*/ + + vec1 = (VectorObject*)v1; /* vector */ scalar = (float)PyFloat_AsDouble(v2); if(scalar==-1.0f && PyErr_Occurred()) { /* parsed item not a number */ @@ -939,9 +864,6 @@ static PyObject *Vector_idiv(PyObject * v1, PyObject * v2) for(i = 0; i < vec1->size; i++) { vec1->vec[i] /= scalar; } - - BaseMath_WriteCallback(vec1); - Py_INCREF( v1 ); return v1; } @@ -952,10 +874,6 @@ static PyObject *Vector_neg(VectorObject *self) { int i; float vec[4]; - - if(!BaseMath_ReadCallback(self)) - return NULL; - for(i = 0; i < self->size; i++){ vec[i] = -self->vec[i]; } @@ -1001,9 +919,6 @@ static PyObject* Vector_richcmpr(PyObject *objectA, PyObject *objectB, int compa vecA = (VectorObject*)objectA; vecB = (VectorObject*)objectB; - if(!BaseMath_ReadCallback(vecA) || !BaseMath_ReadCallback(vecB)) - return NULL; - if (vecA->size != vecB->size){ if (comparison_type == Py_NE){ Py_RETURN_TRUE; @@ -1077,44 +992,6 @@ static PySequenceMethods Vector_SeqMethods = { (ssizessizeobjargproc) Vector_ass_slice, /* sq_ass_slice */ }; -#if (PY_VERSION_HEX >= 0x03000000) -static PyNumberMethods Vector_NumMethods = { - (binaryfunc) Vector_add, /*nb_add*/ - (binaryfunc) Vector_sub, /*nb_subtract*/ - (binaryfunc) Vector_mul, /*nb_multiply*/ - 0, /*nb_remainder*/ - 0, /*nb_divmod*/ - 0, /*nb_power*/ - (unaryfunc) Vector_neg, /*nb_negative*/ - (unaryfunc) 0, /*tp_positive*/ - (unaryfunc) 0, /*tp_absolute*/ - (inquiry) 0, /*tp_bool*/ - (unaryfunc) 0, /*nb_invert*/ - 0, /*nb_lshift*/ - (binaryfunc)0, /*nb_rshift*/ - 0, /*nb_and*/ - 0, /*nb_xor*/ - 0, /*nb_or*/ - 0, /*nb_int*/ - 0, /*nb_reserved*/ - 0, /*nb_float*/ - Vector_iadd, /* nb_inplace_add */ - Vector_isub, /* nb_inplace_subtract */ - Vector_imul, /* nb_inplace_multiply */ - 0, /* nb_inplace_remainder */ - 0, /* nb_inplace_power */ - 0, /* nb_inplace_lshift */ - 0, /* nb_inplace_rshift */ - 0, /* nb_inplace_and */ - 0, /* nb_inplace_xor */ - 0, /* nb_inplace_or */ - 0, /* nb_floor_divide */ - Vector_div, /* nb_true_divide */ - 0, /* nb_inplace_floor_divide */ - Vector_idiv, /* nb_inplace_true_divide */ - 0, /* nb_index */ -}; -#else static PyNumberMethods Vector_NumMethods = { (binaryfunc) Vector_add, /* __add__ */ (binaryfunc) Vector_sub, /* __sub__ */ @@ -1160,8 +1037,6 @@ static PyNumberMethods Vector_NumMethods = { (binaryfunc) NULL, /*__ifloordiv__*/ (binaryfunc) NULL, /*__itruediv__*/ }; -#endif - /*------------------PY_OBECT DEFINITION--------------------------*/ /* @@ -1170,12 +1045,66 @@ static PyNumberMethods Vector_NumMethods = { static PyObject *Vector_getAxis( VectorObject * self, void *type ) { - return Vector_item(self, GET_INT_FROM_POINTER(type)); + switch( (long)type ) { + case 'X': /* these are backwards, but that how it works */ + return PyFloat_FromDouble(self->vec[0]); + case 'Y': + return PyFloat_FromDouble(self->vec[1]); + case 'Z': /* these are backwards, but that how it works */ + if(self->size < 3) { + PyErr_SetString(PyExc_AttributeError, "vector.z: error, cannot get this axis for a 2D vector\n"); + return NULL; + } + else { + return PyFloat_FromDouble(self->vec[2]); + } + case 'W': + if(self->size < 4) { + PyErr_SetString(PyExc_AttributeError, "vector.w: error, cannot get this axis for a 3D vector\n"); + return NULL; + } + + return PyFloat_FromDouble(self->vec[3]); + default: + { + PyErr_SetString( PyExc_RuntimeError, "undefined type in Vector_getAxis" ); + return NULL; + } + } } static int Vector_setAxis( VectorObject * self, PyObject * value, void * type ) { - return Vector_ass_item(self, GET_INT_FROM_POINTER(type), value); + float param= (float)PyFloat_AsDouble( value ); + + if (param==-1 && PyErr_Occurred()) { + PyErr_SetString( PyExc_TypeError, "expected a number for the vector axis" ); + return -1; + } + switch( (long)type ) { + case 'X': /* these are backwards, but that how it works */ + self->vec[0]= param; + break; + case 'Y': + self->vec[1]= param; + break; + case 'Z': /* these are backwards, but that how it works */ + if(self->size < 3) { + PyErr_SetString(PyExc_AttributeError, "vector.z: error, cannot get this axis for a 2D vector\n"); + return -1; + } + self->vec[2]= param; + break; + case 'W': + if(self->size < 4) { + PyErr_SetString(PyExc_AttributeError, "vector.w: error, cannot get this axis for a 3D vector\n"); + return -1; + } + self->vec[3]= param; + break; + } + + return 0; } /* vector.length */ @@ -1184,9 +1113,6 @@ static PyObject *Vector_getLength( VectorObject * self, void *type ) double dot = 0.0f; int i; - if(!BaseMath_ReadCallback(self)) - return NULL; - for(i = 0; i < self->size; i++){ dot += (self->vec[i] * self->vec[i]); } @@ -1198,9 +1124,6 @@ static int Vector_setLength( VectorObject * self, PyObject * value ) double dot = 0.0f, param; int i; - if(!BaseMath_ReadCallback(self)) - return -1; - param= PyFloat_AsDouble( value ); if(param==-1.0 && PyErr_Occurred()) { PyErr_SetString(PyExc_TypeError, "length must be set to a number"); @@ -1236,11 +1159,18 @@ static int Vector_setLength( VectorObject * self, PyObject * value ) self->vec[i]= self->vec[i] / (float)dot; } - BaseMath_WriteCallback(self); /* checked alredy */ - return 0; } +static PyObject *Vector_getWrapped( VectorObject * self, void *type ) +{ + if (self->wrapped == Py_WRAP) + Py_RETURN_TRUE; + else + Py_RETURN_FALSE; +} + + /* Get a new Vector according to the provided swizzle. This function has little error checking, as we are in control of the inputs: the closure is set by us in Vector_createSwizzleGetSeter. */ @@ -1251,9 +1181,6 @@ static PyObject *Vector_getSwizzle(VectorObject * self, void *closure) float vec[MAX_DIMENSIONS]; unsigned int swizzleClosure; - if(!BaseMath_ReadCallback(self)) - return NULL; - /* Unpack the axes from the closure into an array. */ axisA = 0; swizzleClosure = (unsigned int) closure; @@ -1291,9 +1218,6 @@ static int Vector_setSwizzle(VectorObject * self, PyObject * value, void *closur float vecTemp[MAX_DIMENSIONS]; - if(!BaseMath_ReadCallback(self)) - return -1; - /* Check that the closure can be used with this vector: even 2D vectors have swizzles defined for axes z and w, but they would be invalid. */ swizzleClosure = (unsigned int) closure; @@ -1323,7 +1247,7 @@ static int Vector_setSwizzle(VectorObject * self, PyObject * value, void *closur axisB++; } memcpy(self->vec, vecTemp, axisB * sizeof(float)); - /* continue with BaseMathObject_WriteCallback at the end */ + return 0; } else if (PyList_Check(value)) { @@ -1349,7 +1273,7 @@ static int Vector_setSwizzle(VectorObject * self, PyObject * value, void *closur axisB++; } memcpy(self->vec, vecTemp, axisB * sizeof(float)); - /* continue with BaseMathObject_WriteCallback at the end */ + return 0; } else if (((scalarVal = (float)PyFloat_AsDouble(value)) == -1.0 && PyErr_Occurred())==0) { @@ -1362,17 +1286,13 @@ static int Vector_setSwizzle(VectorObject * self, PyObject * value, void *closur swizzleClosure = swizzleClosure >> SWIZZLE_BITS_PER_AXIS; } - /* continue with BaseMathObject_WriteCallback at the end */ + return 0; } - else { + else + { PyErr_SetString( PyExc_TypeError, "Expected a Vector, list or scalar value." ); return -1; } - - if(!BaseMath_WriteCallback(vecVal)) - return -1; - else - return 0; } /*****************************************************************************/ @@ -1382,19 +1302,19 @@ static PyGetSetDef Vector_getseters[] = { {"x", (getter)Vector_getAxis, (setter)Vector_setAxis, "Vector X axis", - (void *)0}, + (void *)'X'}, {"y", (getter)Vector_getAxis, (setter)Vector_setAxis, "Vector Y axis", - (void *)1}, + (void *)'Y'}, {"z", (getter)Vector_getAxis, (setter)Vector_setAxis, "Vector Z axis", - (void *)2}, + (void *)'Z'}, {"w", (getter)Vector_getAxis, (setter)Vector_setAxis, "Vector Z axis", - (void *)3}, + (void *)'W'}, {"length", (getter)Vector_getLength, (setter)Vector_setLength, "Vector Length", @@ -1404,13 +1324,9 @@ static PyGetSetDef Vector_getseters[] = { "Vector Length", NULL}, {"wrapped", - (getter)BaseMathObject_getWrapped, (setter)NULL, + (getter)Vector_getWrapped, (setter)NULL, "True when this wraps blenders internal data", NULL}, - {"__owner__", - (getter)BaseMathObject_getOwner, (setter)NULL, - "Read only owner for vectors that depend on another object", - NULL}, /* autogenerated swizzle attrs, see python script below */ {"xx", (getter)Vector_getSwizzle, (setter)Vector_setSwizzle, Vector_swizzle_doc, (void *)((unsigned int)((0|SWIZZLE_VALID_AXIS) | ((0|SWIZZLE_VALID_AXIS)<<SWIZZLE_BITS_PER_AXIS)))}, /* 36 */ @@ -1811,13 +1727,13 @@ PyTypeObject vector_Type = { 0, /* ob_size */ #endif /* For printing, in format "<module>.<name>" */ - "vector", /* char *tp_name; */ + "Blender Vector", /* char *tp_name; */ sizeof( VectorObject ), /* int tp_basicsize; */ 0, /* tp_itemsize; For allocation */ /* Methods to implement standard operations */ - ( destructor ) BaseMathObject_dealloc,/* destructor tp_dealloc; */ + ( destructor ) Vector_dealloc,/* destructor tp_dealloc; */ NULL, /* printfunc tp_print; */ NULL, /* getattrfunc tp_getattr; */ NULL, /* setattrfunc tp_setattr; */ @@ -1903,10 +1819,6 @@ PyObject *newVectorObject(float *vec, int size, int type) if(size > 4 || size < 2) return NULL; self->size = size; - - /* init callbacks as NULL */ - self->cb_user= NULL; - self->cb_type= self->cb_subtype= 0; if(type == Py_WRAP) { self->vec = vec; @@ -1931,72 +1843,20 @@ PyObject *newVectorObject(float *vec, int size, int type) return (PyObject *) self; } -PyObject *newVectorObject_cb(PyObject *cb_user, int size, int cb_type, int cb_subtype) -{ - float dummy[4] = {0.0, 0.0, 0.0, 0.0}; /* dummy init vector, callbacks will be used on access */ - VectorObject *self= (VectorObject *)newVectorObject(dummy, size, Py_NEW); - if(self) { - Py_INCREF(cb_user); - self->cb_user= cb_user; - self->cb_type= (unsigned char)cb_type; - self->cb_subtype= (unsigned char)cb_subtype; - } - - return (PyObject *)self; -} - -//-----------------row_vector_multiplication (internal)----------- -//ROW VECTOR Multiplication - Vector X Matrix -//[x][y][z] * [1][2][3] -// [4][5][6] -// [7][8][9] -//vector/matrix multiplication IS NOT COMMUTATIVE!!!! -static PyObject *row_vector_multiplication(VectorObject* vec, MatrixObject * mat) -{ - float vecNew[4], vecCopy[4]; - double dot = 0.0f; - int x, y, z = 0, vec_size = vec->size; - - if(mat->colSize != vec_size){ - if(mat->rowSize == 4 && vec_size != 3){ - PyErr_SetString(PyExc_AttributeError, "vector * matrix: matrix column size and the vector size must be the same"); - return NULL; - }else{ - vecCopy[3] = 1.0f; - } - } - - if(!BaseMath_ReadCallback(vec) || !BaseMath_ReadCallback(mat)) - return NULL; - - for(x = 0; x < vec_size; x++){ - vecCopy[x] = vec->vec[x]; - } - - //muliplication - for(x = 0; x < mat->colSize; x++) { - for(y = 0; y < mat->rowSize; y++) { - dot += mat->matrix[y][x] * vecCopy[y]; - } - vecNew[z++] = (float)dot; - dot = 0.0f; - } - return newVectorObject(vecNew, vec_size, Py_NEW); -} - -/*----------------------------Vector.negate() -------------------- +/* + #############################DEPRECATED################################ + ####################################################################### + ----------------------------Vector.negate() -------------------- set the vector to it's negative -x, -y, -z */ static PyObject *Vector_Negate(VectorObject * self) { int i; - if(!BaseMath_ReadCallback(self)) - return NULL; - - for(i = 0; i < self->size; i++) + for(i = 0; i < self->size; i++) { self->vec[i] = -(self->vec[i]); - - BaseMath_WriteCallback(self); // alredy checked for error - + } + /*printf("Vector.negate(): Deprecated: use -vector instead\n");*/ Py_INCREF(self); return (PyObject*)self; } +/*################################################################### + ###########################DEPRECATED##############################*/ diff --git a/source/blender/python/generic/vector.h b/source/blender/python/generic/vector.h index f519b2808cb..d2eb826ef10 100644 --- a/source/blender/python/generic/vector.h +++ b/source/blender/python/generic/vector.h @@ -1,4 +1,4 @@ -/* $Id$ +/* $Id: vector.h 20332 2009-05-22 03:22:56Z campbellbarton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -37,20 +37,14 @@ extern PyTypeObject vector_Type; #define VectorObject_Check(v) (((PyObject *)v)->ob_type == &vector_Type) -typedef struct { /* keep aligned with BaseMathObject in Mathutils.h */ +typedef struct { PyObject_VAR_HEAD - float *vec; /*1D array of data (alias), wrapped status depends on wrapped status */ - PyObject *cb_user; /* if this vector references another object, otherwise NULL, *Note* this owns its reference */ - unsigned char cb_type; /* which user funcs do we adhere to, RNA, GameObject, etc */ - unsigned char cb_subtype; /* subtype: location, rotation... to avoid defining many new functions for every attribute of the same type */ - unsigned char wrapped; /* wrapped data type? */ - /* end BaseMathObject */ - - unsigned char size; /* vec size 2,3 or 4 */ + float *vec; /*1D array of data (alias), wrapped status depends on wrapped status */ + short size; /* vec size 2,3 or 4 */ + short wrapped; /* is wrapped data? */ } VectorObject; /*prototypes*/ PyObject *newVectorObject(float *vec, int size, int type); -PyObject *newVectorObject_cb(PyObject *user, int size, int callback_type, int subtype); #endif /* EXPP_vector_h */ diff --git a/source/blender/python/intern/Makefile b/source/blender/python/intern/Makefile index d210cfaf973..0c4a540a4bd 100644 --- a/source/blender/python/intern/Makefile +++ b/source/blender/python/intern/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 11904 2007-08-31 16:16:33Z sirdude $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/python/intern/bpy_compat.h b/source/blender/python/intern/bpy_compat.h index 1ad9376c13b..032b60988d5 100644 --- a/source/blender/python/intern/bpy_compat.h +++ b/source/blender/python/intern/bpy_compat.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: bpy_compat.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/python/intern/bpy_interface.c b/source/blender/python/intern/bpy_interface.c index 8b5ad36f349..559ed537757 100644 --- a/source/blender/python/intern/bpy_interface.c +++ b/source/blender/python/intern/bpy_interface.c @@ -37,11 +37,6 @@ #include "BPY_extern.h" #include "../generic/bpy_internal_import.h" // our own imports -/* external util modukes */ - -#include "../generic/Mathutils.h" -#include "../generic/Geometry.h" -#include "../generic/BGL.h" void BPY_free_compiled_text( struct Text *text ) @@ -66,17 +61,11 @@ static void bpy_init_modules( void ) PyModule_AddObject( mod, "types", BPY_rna_types() ); PyModule_AddObject( mod, "props", BPY_rna_props() ); PyModule_AddObject( mod, "ops", BPY_operator_module() ); - PyModule_AddObject( mod, "ui", BPY_ui_module() ); // XXX very experimental, consider this a test, especially PyCObject is not meant to be permanent + PyModule_AddObject( mod, "ui", BPY_ui_module() ); // XXX very experemental, consider this a test, especially PyCObject is not meant to be perminant /* add the module so we can import it */ PyDict_SetItemString(PySys_GetObject("modules"), "bpy", mod); Py_DECREF(mod); - - - /* stand alone utility modules not related to blender directly */ - Geometry_Init("Geometry"); - Mathutils_Init("Mathutils"); - BGL_Init("BGL"); } #if (PY_VERSION_HEX < 0x02050000) diff --git a/source/blender/python/intern/bpy_operator.c b/source/blender/python/intern/bpy_operator.c index 004cf2fb7c7..3ea330adc85 100644 --- a/source/blender/python/intern/bpy_operator.c +++ b/source/blender/python/intern/bpy_operator.c @@ -1,6 +1,6 @@ /** - * $Id$ + * $Id: bpy_operator.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/python/intern/bpy_operator.h b/source/blender/python/intern/bpy_operator.h index 46ea144fd4d..8a4493b5866 100644 --- a/source/blender/python/intern/bpy_operator.h +++ b/source/blender/python/intern/bpy_operator.h @@ -1,6 +1,6 @@ /** - * $Id$ + * $Id: bpy_operator.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/python/intern/bpy_operator_wrap.c b/source/blender/python/intern/bpy_operator_wrap.c index b7e3c86dd91..3d5427ddefd 100644 --- a/source/blender/python/intern/bpy_operator_wrap.c +++ b/source/blender/python/intern/bpy_operator_wrap.c @@ -1,6 +1,6 @@ /** - * $Id$ + * $Id: bpy_operator_wrap.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -47,6 +47,98 @@ #define PYOP_ATTR_IDNAME "__name__" /* use pythons class name */ #define PYOP_ATTR_DESCRIPTION "__doc__" /* use pythons docstring */ +static PyObject *pyop_dict_from_event(wmEvent *event) +{ + PyObject *dict= PyDict_New(); + PyObject *item; + char *cstring, ascii[2]; + + /* type */ + item= PyUnicode_FromString(WM_key_event_string(event->type)); + PyDict_SetItemString(dict, "type", item); Py_DECREF(item); + + /* val */ + switch(event->val) { + case KM_ANY: + cstring = "ANY"; + break; + case KM_RELEASE: + cstring = "RELEASE"; + break; + case KM_PRESS: + cstring = "PRESS"; + break; + default: + cstring = "UNKNOWN"; + break; + } + + item= PyUnicode_FromString(cstring); + PyDict_SetItemString(dict, "val", item); Py_DECREF(item); + + /* x, y (mouse) */ + item= PyLong_FromLong(event->x); + PyDict_SetItemString(dict, "x", item); Py_DECREF(item); + + item= PyLong_FromLong(event->y); + PyDict_SetItemString(dict, "y", item); Py_DECREF(item); + + item= PyLong_FromLong(event->prevx); + PyDict_SetItemString(dict, "prevx", item); Py_DECREF(item); + + item= PyLong_FromLong(event->prevy); + PyDict_SetItemString(dict, "prevy", item); Py_DECREF(item); + + /* ascii */ + ascii[0]= event->ascii; + ascii[1]= '\0'; + item= PyUnicode_FromString(ascii); + PyDict_SetItemString(dict, "ascii", item); Py_DECREF(item); + + /* modifier keys */ + item= PyLong_FromLong(event->shift); + PyDict_SetItemString(dict, "shift", item); Py_DECREF(item); + + item= PyLong_FromLong(event->ctrl); + PyDict_SetItemString(dict, "ctrl", item); Py_DECREF(item); + + item= PyLong_FromLong(event->alt); + PyDict_SetItemString(dict, "alt", item); Py_DECREF(item); + + item= PyLong_FromLong(event->oskey); + PyDict_SetItemString(dict, "oskey", item); Py_DECREF(item); + + + + /* modifier */ +#if 0 + item= PyTuple_New(0); + if(event->keymodifier & KM_SHIFT) { + _PyTuple_Resize(&item, size+1); + PyTuple_SET_ITEM(item, size, _PyUnicode_AsString("SHIFT")); + size++; + } + if(event->keymodifier & KM_CTRL) { + _PyTuple_Resize(&item, size+1); + PyTuple_SET_ITEM(item, size, _PyUnicode_AsString("CTRL")); + size++; + } + if(event->keymodifier & KM_ALT) { + _PyTuple_Resize(&item, size+1); + PyTuple_SET_ITEM(item, size, _PyUnicode_AsString("ALT")); + size++; + } + if(event->keymodifier & KM_OSKEY) { + _PyTuple_Resize(&item, size+1); + PyTuple_SET_ITEM(item, size, _PyUnicode_AsString("OSKEY")); + size++; + } + PyDict_SetItemString(dict, "keymodifier", item); Py_DECREF(item); +#endif + + return dict; +} + static struct BPY_flag_def pyop_ret_flags[] = { {"RUNNING_MODAL", OPERATOR_RUNNING_MODAL}, {"CANCELLED", OPERATOR_CANCELLED}, @@ -88,7 +180,6 @@ static int PYTHON_OT_generic(int mode, bContext *C, wmOperator *op, wmEvent *eve int ret_flag= (mode==PYOP_POLL ? 0:OPERATOR_CANCELLED); PointerRNA ptr_context; PointerRNA ptr_operator; - PointerRNA ptr_event; PyObject *py_operator; PyGILState_STATE gilstate = PyGILState_Ensure(); @@ -107,9 +198,15 @@ static int PYTHON_OT_generic(int mode, bContext *C, wmOperator *op, wmEvent *eve /* Assign instance attributes from operator properties */ { + PropertyRNA *prop, *iterprop; + CollectionPropertyIterator iter; const char *arg_name; - RNA_STRUCT_BEGIN(op->ptr, prop) { + iterprop= RNA_struct_iterator_property(op->ptr->type); + RNA_property_collection_begin(op->ptr, iterprop, &iter); + + for(; iter.valid; RNA_property_collection_next(&iter)) { + prop= iter.ptr.data; arg_name= RNA_property_identifier(prop); if (strcmp(arg_name, "rna_type")==0) continue; @@ -118,7 +215,8 @@ static int PYTHON_OT_generic(int mode, bContext *C, wmOperator *op, wmEvent *eve PyObject_SetAttrString(py_class_instance, arg_name, item); Py_DECREF(item); } - RNA_STRUCT_END; + + RNA_property_collection_end(&iter); } /* set operator pointer RNA as instance "__operator__" attribute */ @@ -132,13 +230,11 @@ static int PYTHON_OT_generic(int mode, bContext *C, wmOperator *op, wmEvent *eve if (mode==PYOP_INVOKE) { item= PyObject_GetAttrString(py_class, "invoke"); args = PyTuple_New(3); - - RNA_pointer_create(NULL, &RNA_Event, event, &ptr_event); // PyTuple_SET_ITEM "steals" object reference, it is // an object passed shouldn't be DECREF'ed PyTuple_SET_ITEM(args, 1, pyrna_struct_CreatePyObject(&ptr_context)); - PyTuple_SET_ITEM(args, 2, pyrna_struct_CreatePyObject(&ptr_event)); + PyTuple_SET_ITEM(args, 2, pyop_dict_from_event(event)); } else if (mode==PYOP_EXEC) { item= PyObject_GetAttrString(py_class, "execute"); diff --git a/source/blender/python/intern/bpy_operator_wrap.h b/source/blender/python/intern/bpy_operator_wrap.h index 2929d57ab82..c9efb1ea22f 100644 --- a/source/blender/python/intern/bpy_operator_wrap.h +++ b/source/blender/python/intern/bpy_operator_wrap.h @@ -1,6 +1,6 @@ /** - * $Id$ + * $Id: bpy_operator_wrap.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/python/intern/bpy_rna.c b/source/blender/python/intern/bpy_rna.c index f07c85f7083..d131361294d 100644 --- a/source/blender/python/intern/bpy_rna.c +++ b/source/blender/python/intern/bpy_rna.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: bpy_rna.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -39,94 +39,6 @@ #include "BKE_global.h" /* evil G.* */ #include "BKE_report.h" -#define USE_MATHUTILS - -#ifdef USE_MATHUTILS -#include "../generic/Mathutils.h" /* so we can have mathutils callbacks */ - -/* bpyrna vector/euler/quat callbacks */ -static int mathutils_rna_array_cb_index= -1; /* index for our callbacks */ - -static int mathutils_rna_generic_check(BPy_PropertyRNA *self) -{ - return self->prop?1:0; -} - -static int mathutils_rna_vector_get(BPy_PropertyRNA *self, int subtype, float *vec_from) -{ - if(self->prop==NULL) - return 0; - - RNA_property_float_get_array(&self->ptr, self->prop, vec_from); - return 1; -} - -static int mathutils_rna_vector_set(BPy_PropertyRNA *self, int subtype, float *vec_to) -{ - if(self->prop==NULL) - return 0; - - RNA_property_float_set_array(&self->ptr, self->prop, vec_to); - return 1; -} - -static int mathutils_rna_vector_get_index(BPy_PropertyRNA *self, int subtype, float *vec_from, int index) -{ - if(self->prop==NULL) - return 0; - - vec_from[index]= RNA_property_float_get_index(&self->ptr, self->prop, index); - return 1; -} - -static int mathutils_rna_vector_set_index(BPy_PropertyRNA *self, int subtype, float *vec_to, int index) -{ - if(self->prop==NULL) - return 0; - - RNA_property_float_set_index(&self->ptr, self->prop, index, vec_to[index]); - return 1; -} - -Mathutils_Callback mathutils_rna_array_cb = { - mathutils_rna_generic_check, - mathutils_rna_vector_get, - mathutils_rna_vector_set, - mathutils_rna_vector_get_index, - mathutils_rna_vector_set_index -}; - -/* bpyrna matrix callbacks */ -static int mathutils_rna_matrix_cb_index= -1; /* index for our callbacks */ - -static int mathutils_rna_matrix_get(BPy_PropertyRNA *self, int subtype, float *mat_from) -{ - if(self->prop==NULL) - return 0; - - RNA_property_float_get_array(&self->ptr, self->prop, mat_from); - return 1; -} - -static int mathutils_rna_matrix_set(BPy_PropertyRNA *self, int subtype, float *mat_to) -{ - if(self->prop==NULL) - return 0; - - RNA_property_float_set_array(&self->ptr, self->prop, mat_to); - return 1; -} - -Mathutils_Callback mathutils_rna_matrix_cb = { - mathutils_rna_generic_check, - mathutils_rna_matrix_get, - mathutils_rna_matrix_set, - NULL, - NULL -}; - -#endif - static int pyrna_struct_compare( BPy_StructRNA * a, BPy_StructRNA * b ) { return (a->ptr.data==b->ptr.data) ? 0 : -1; @@ -161,15 +73,14 @@ static PyObject *pyrna_prop_richcmp(BPy_PropertyRNA * a, BPy_PropertyRNA * b, in /*----------------------repr--------------------------------------------*/ static PyObject *pyrna_struct_repr( BPy_StructRNA * self ) { - PyObject *pyob; - char *name; + PropertyRNA *prop; + char str[512]; /* print name if available */ - name= RNA_struct_name_get_alloc(&self->ptr, NULL, 0); - if(name) { - pyob= PyUnicode_FromFormat( "[BPy_StructRNA \"%s\" -> \"%s\"]", RNA_struct_identifier(self->ptr.type), name); - MEM_freeN(name); - return pyob; + prop= RNA_struct_name_property(self->ptr.type); + if(prop) { + RNA_property_string_get(&self->ptr, prop, str); + return PyUnicode_FromFormat( "[BPy_StructRNA \"%s\" -> \"%s\"]", RNA_struct_identifier(self->ptr.type), str); } return PyUnicode_FromFormat( "[BPy_StructRNA \"%s\"]", RNA_struct_identifier(self->ptr.type)); @@ -177,19 +88,20 @@ static PyObject *pyrna_struct_repr( BPy_StructRNA * self ) static PyObject *pyrna_prop_repr( BPy_PropertyRNA * self ) { - PyObject *pyob; + PropertyRNA *prop; PointerRNA ptr; - char *name; + char str[512]; /* if a pointer, try to print name of pointer target too */ if(RNA_property_type(self->prop) == PROP_POINTER) { ptr= RNA_property_pointer_get(&self->ptr, self->prop); - name= RNA_struct_name_get_alloc(&ptr, NULL, 0); - if(name) { - pyob= PyUnicode_FromFormat( "[BPy_PropertyRNA \"%s\" -> \"%s\" -> \"%s\" ]", RNA_struct_identifier(self->ptr.type), RNA_property_identifier(self->prop), name); - MEM_freeN(name); - return pyob; + if(ptr.data) { + prop= RNA_struct_name_property(ptr.type); + if(prop) { + RNA_property_string_get(&ptr, prop, str); + return PyUnicode_FromFormat( "[BPy_PropertyRNA \"%s\" -> \"%s\" -> \"%s\" ]", RNA_struct_identifier(self->ptr.type), RNA_property_identifier(self->prop), str); + } } } @@ -204,13 +116,13 @@ static long pyrna_struct_hash( BPy_StructRNA * self ) /* use our own dealloc so we can free a property if we use one */ static void pyrna_struct_dealloc( BPy_StructRNA * self ) { + /* Note!! for some weired reason calling PyObject_DEL() directly crashes blender! */ if (self->freeptr && self->ptr.data) { IDP_FreeProperty(self->ptr.data); MEM_freeN(self->ptr.data); self->ptr.data= NULL; } - /* Note, for subclassed PyObjects we cant just call PyObject_DEL() directly or it will crash */ Py_TYPE(self)->tp_free(self); return; } @@ -218,8 +130,9 @@ static void pyrna_struct_dealloc( BPy_StructRNA * self ) static char *pyrna_enum_as_string(PointerRNA *ptr, PropertyRNA *prop) { const EnumPropertyItem *item; + int totitem; - RNA_property_enum_items(ptr, prop, &item, NULL); + RNA_property_enum_items(ptr, prop, &item, &totitem); return (char*)BPy_enum_as_string((EnumPropertyItem*)item); } @@ -231,52 +144,7 @@ PyObject * pyrna_prop_to_py(PointerRNA *ptr, PropertyRNA *prop) if (len > 0) { /* resolve the array from a new pytype */ - PyObject *ret = pyrna_prop_CreatePyObject(ptr, prop); - -#ifdef USE_MATHUTILS - - /* return a mathutils vector where possible */ - if(RNA_property_type(prop)==PROP_FLOAT) { - switch(RNA_property_subtype(prop)) { - case PROP_VECTOR: - if(len>=2 && len <= 4) { - PyObject *vec_cb= newVectorObject_cb(ret, len, mathutils_rna_array_cb_index, 0); - Py_DECREF(ret); /* the vector owns now */ - ret= vec_cb; /* return the vector instead */ - } - break; - case PROP_MATRIX: - if(len==16) { - PyObject *mat_cb= newMatrixObject_cb(ret, 4,4, mathutils_rna_matrix_cb_index, 0); - Py_DECREF(ret); /* the matrix owns now */ - ret= mat_cb; /* return the matrix instead */ - } - else if (len==9) { - PyObject *mat_cb= newMatrixObject_cb(ret, 3,3, mathutils_rna_matrix_cb_index, 0); - Py_DECREF(ret); /* the matrix owns now */ - ret= mat_cb; /* return the matrix instead */ - } - break; - case PROP_ROTATION: - if(len==3) { /* euler */ - PyObject *eul_cb= newEulerObject_cb(ret, mathutils_rna_array_cb_index, 0); - Py_DECREF(ret); /* the matrix owns now */ - ret= eul_cb; /* return the matrix instead */ - } - else if (len==4) { - PyObject *quat_cb= newQuaternionObject_cb(ret, mathutils_rna_array_cb_index, 0); - Py_DECREF(ret); /* the matrix owns now */ - ret= quat_cb; /* return the matrix instead */ - } - break; - default: - break; - } - } - -#endif - - return ret; + return pyrna_prop_CreatePyObject(ptr, prop); } /* see if we can coorce into a python type - PropertyType */ @@ -345,9 +213,17 @@ int pyrna_pydict_to_props(PointerRNA *ptr, PyObject *kw, const char *error_prefi const char *arg_name= NULL; PyObject *item; + PropertyRNA *prop, *iterprop; + CollectionPropertyIterator iter; + + iterprop= RNA_struct_iterator_property(ptr->type); + RNA_property_collection_begin(ptr, iterprop, &iter); + totkw = kw ? PyDict_Size(kw):0; - RNA_STRUCT_BEGIN(ptr, prop) { + for(; iter.valid; RNA_property_collection_next(&iter)) { + prop= iter.ptr.data; + arg_name= RNA_property_identifier(prop); if (strcmp(arg_name, "rna_type")==0) continue; @@ -373,7 +249,8 @@ int pyrna_pydict_to_props(PointerRNA *ptr, PyObject *kw, const char *error_prefi totkw--; } - RNA_STRUCT_END; + + RNA_property_collection_end(&iter); if (error_val==0 && totkw > 0) { /* some keywords were given that were not used :/ */ PyObject *key, *value; @@ -394,15 +271,12 @@ int pyrna_pydict_to_props(PointerRNA *ptr, PyObject *kw, const char *error_prefi static PyObject * pyrna_func_call(PyObject * self, PyObject *args, PyObject *kw); -PyObject *pyrna_func_to_py(BPy_StructRNA *pyrna, FunctionRNA *func) +PyObject *pyrna_func_to_py(PointerRNA *ptr, FunctionRNA *func) { static PyMethodDef func_meth = {"<generic rna function>", (PyCFunction)pyrna_func_call, METH_VARARGS|METH_KEYWORDS, "python rna function"}; PyObject *self= PyTuple_New(2); PyObject *ret; - - PyTuple_SET_ITEM(self, 0, (PyObject *)pyrna); - Py_INCREF(pyrna); - + PyTuple_SET_ITEM(self, 0, pyrna_struct_CreatePyObject(ptr)); PyTuple_SET_ITEM(self, 1, PyCObject_FromVoidPtr((void *)func, NULL)); ret= PyCFunction_New(&func_meth, self); @@ -420,30 +294,15 @@ int pyrna_py_to_prop(PointerRNA *ptr, PropertyRNA *prop, void *data, PyObject *v if (len > 0) { PyObject *item; - int py_len = -1; int i; - -#ifdef USE_MATHUTILS - if(MatrixObject_Check(value)) { - MatrixObject *mat = (MatrixObject*)value; - if(!BaseMath_ReadCallback(mat)) - return -1; - - py_len = mat->rowSize * mat->colSize; - } else /* continue... */ -#endif - if (PySequence_Check(value)) { - py_len= (int)PySequence_Length(value); - } - else { - PyErr_Format(PyExc_TypeError, "RNA array assignment expected a sequence instead of %s instance.", Py_TYPE(value)->tp_name); + if (!PySequence_Check(value)) { + PyErr_SetString(PyExc_TypeError, "expected a python sequence type assigned to an RNA array."); return -1; } - /* done getting the length */ - if (py_len != len) { - PyErr_Format(PyExc_AttributeError, "python sequence length %d did not match the RNA array length %d.", py_len, len); + if ((int)PySequence_Length(value) != len) { + PyErr_SetString(PyExc_AttributeError, "python sequence length did not match the RNA array."); return -1; } @@ -509,21 +368,14 @@ int pyrna_py_to_prop(PointerRNA *ptr, PropertyRNA *prop, void *data, PyObject *v else param_arr = MEM_mallocN(sizeof(float) * len, "pyrna float array"); -#ifdef USE_MATHUTILS - if(MatrixObject_Check(value) && RNA_property_subtype(prop) == PROP_MATRIX) { - MatrixObject *mat = (MatrixObject*)value; - memcpy(param_arr, mat->contigPtr, sizeof(float) * len); - } else /* continue... */ -#endif - { - /* collect the variables */ - for (i=0; i<len; i++) { - item = PySequence_GetItem(value, i); - param_arr[i] = (float)PyFloat_AsDouble(item); /* deal with any errors later */ - Py_DECREF(item); - } + + /* collect the variables */ + for (i=0; i<len; i++) { + item = PySequence_GetItem(value, i); + param_arr[i] = (float)PyFloat_AsDouble(item); /* deal with any errors later */ + Py_DECREF(item); } - + if (PyErr_Occurred()) { if(data==NULL) MEM_freeN(param_arr); @@ -679,10 +531,6 @@ int pyrna_py_to_prop(PointerRNA *ptr, PropertyRNA *prop, void *data, PyObject *v int seq_len, i; PyObject *item; PointerRNA itemptr; - ListBase *lb; - CollectionPointerLink *link; - - lb= (data)? (ListBase*)data: NULL; /* convert a sequence of dict's into a collection */ if(!PySequence_Check(value)) { @@ -698,15 +546,8 @@ int pyrna_py_to_prop(PointerRNA *ptr, PropertyRNA *prop, void *data, PyObject *v Py_XDECREF(item); return -1; } - - if(lb) { - link= MEM_callocN(sizeof(CollectionPointerLink), "PyCollectionPointerLink"); - link->ptr= itemptr; - BLI_addtail(lb, link); - } - else - RNA_property_collection_add(ptr, prop, &itemptr); - + + RNA_property_collection_add(ptr, prop, &itemptr); if(pyrna_pydict_to_props(&itemptr, item, "Converting a python list to an RNA collection")==-1) { Py_DECREF(item); return -1; @@ -963,6 +804,7 @@ static PyObject *pyrna_struct_dir(BPy_StructRNA * self) PyObject *pystring; /* for looping over attrs and funcs */ + CollectionPropertyIterator iter; PropertyRNA *iterprop; /* Include this incase this instance is a subtype of a python class @@ -991,23 +833,26 @@ static PyObject *pyrna_struct_dir(BPy_StructRNA * self) /* * Collect RNA attributes */ + PropertyRNA *nameprop; char name[256], *nameptr; iterprop= RNA_struct_iterator_property(self->ptr.type); + RNA_property_collection_begin(&self->ptr, iterprop, &iter); - RNA_PROP_BEGIN(&self->ptr, itemptr, iterprop) { - nameptr= RNA_struct_name_get_alloc(&itemptr, name, sizeof(name)); - - if(nameptr) { + for(; iter.valid; RNA_property_collection_next(&iter)) { + if(iter.ptr.data && (nameprop = RNA_struct_name_property(iter.ptr.type))) { + nameptr= RNA_property_string_get_alloc(&iter.ptr, nameprop, name, sizeof(name)); + pystring = PyUnicode_FromString(nameptr); PyList_Append(ret, pystring); Py_DECREF(pystring); - if(name != nameptr) + if ((char *)&name != nameptr) MEM_freeN(nameptr); } } - RNA_PROP_END; + RNA_property_collection_end(&iter); + } @@ -1020,12 +865,15 @@ static PyObject *pyrna_struct_dir(BPy_StructRNA * self) RNA_pointer_create(NULL, &RNA_Struct, self->ptr.type, &tptr); iterprop= RNA_struct_find_property(&tptr, "functions"); - RNA_PROP_BEGIN(&tptr, itemptr, iterprop) { - pystring = PyUnicode_FromString(RNA_function_identifier(itemptr.data)); + RNA_property_collection_begin(&tptr, iterprop, &iter); + + for(; iter.valid; RNA_property_collection_next(&iter)) { + pystring = PyUnicode_FromString(RNA_function_identifier(iter.ptr.data)); PyList_Append(ret, pystring); Py_DECREF(pystring); } - RNA_PROP_END; + + RNA_property_collection_end(&iter); } if(self->ptr.type == &RNA_Context) { @@ -1067,7 +915,7 @@ static PyObject *pyrna_struct_getattro( BPy_StructRNA * self, PyObject *pyname ) ret = pyrna_prop_to_py(&self->ptr, prop); } else if ((func = RNA_struct_find_function(&self->ptr, name))) { - ret = pyrna_func_to_py(self, func); + ret = pyrna_func_to_py(&self->ptr, func); } else if (self->ptr.type == &RNA_Context) { PointerRNA newptr; @@ -1138,25 +986,28 @@ PyObject *pyrna_prop_keys(BPy_PropertyRNA *self) ret = NULL; } else { PyObject *item; + CollectionPropertyIterator iter; + PropertyRNA *nameprop; char name[256], *nameptr; ret = PyList_New(0); - RNA_PROP_BEGIN(&self->ptr, itemptr, self->prop) { - nameptr= RNA_struct_name_get_alloc(&itemptr, name, sizeof(name)); - - if(nameptr) { + RNA_property_collection_begin(&self->ptr, self->prop, &iter); + for(; iter.valid; RNA_property_collection_next(&iter)) { + if(iter.ptr.data && (nameprop = RNA_struct_name_property(iter.ptr.type))) { + nameptr= RNA_property_string_get_alloc(&iter.ptr, nameprop, name, sizeof(name)); + /* add to python list */ item = PyUnicode_FromString( nameptr ); PyList_Append(ret, item); Py_DECREF(item); /* done */ - if(name != nameptr) + if ((char *)&name != nameptr) MEM_freeN(nameptr); } } - RNA_PROP_END; + RNA_property_collection_end(&iter); } return ret; @@ -1170,25 +1021,28 @@ PyObject *pyrna_prop_items(BPy_PropertyRNA *self) ret = NULL; } else { PyObject *item; + CollectionPropertyIterator iter; + PropertyRNA *nameprop; char name[256], *nameptr; int i= 0; ret = PyList_New(0); - RNA_PROP_BEGIN(&self->ptr, itemptr, self->prop) { - if(itemptr.data) { + RNA_property_collection_begin(&self->ptr, self->prop, &iter); + for(; iter.valid; RNA_property_collection_next(&iter)) { + if(iter.ptr.data) { /* add to python list */ item= PyTuple_New(2); - nameptr= RNA_struct_name_get_alloc(&itemptr, name, sizeof(name)); - if(nameptr) { + if(nameprop = RNA_struct_name_property(iter.ptr.type)) { + nameptr= RNA_property_string_get_alloc(&iter.ptr, nameprop, name, sizeof(name)); PyTuple_SET_ITEM(item, 0, PyUnicode_FromString( nameptr )); - if(name != nameptr) + if ((char *)&name != nameptr) MEM_freeN(nameptr); } else { PyTuple_SET_ITEM(item, 0, PyLong_FromSsize_t(i)); /* a bit strange but better then returning an empty list */ } - PyTuple_SET_ITEM(item, 1, pyrna_struct_CreatePyObject(&itemptr)); + PyTuple_SET_ITEM(item, 1, pyrna_struct_CreatePyObject(&iter.ptr)); PyList_Append(ret, item); Py_DECREF(item); @@ -1196,7 +1050,7 @@ PyObject *pyrna_prop_items(BPy_PropertyRNA *self) i++; } } - RNA_PROP_END; + RNA_property_collection_end(&iter); } return ret; @@ -1212,14 +1066,18 @@ PyObject *pyrna_prop_values(BPy_PropertyRNA *self) ret = NULL; } else { PyObject *item; + CollectionPropertyIterator iter; + PropertyRNA *iterprop; ret = PyList_New(0); - RNA_PROP_BEGIN(&self->ptr, itemptr, self->prop) { - item = pyrna_struct_CreatePyObject(&itemptr); + //iterprop= RNA_struct_iterator_property(self->ptr.type); + RNA_property_collection_begin(&self->ptr, self->prop, &iter); + for(; iter.valid; RNA_property_collection_next(&iter)) { + item = pyrna_struct_CreatePyObject(&iter.ptr); PyList_Append(ret, item); Py_DECREF(item); } - RNA_PROP_END; + RNA_property_collection_end(&iter); } return ret; @@ -1393,21 +1251,10 @@ PyObject *pyrna_param_to_py(PointerRNA *ptr, PropertyRNA *prop, void *data) break; } case PROP_COLLECTION: - { - ListBase *lb= (ListBase*)data; - CollectionPointerLink *link; - PyObject *linkptr; - - ret = PyList_New(0); - - for(link=lb->first; link; link=link->next) { - linkptr= pyrna_struct_CreatePyObject(&link->ptr); - PyList_Append(ret, linkptr); - Py_DECREF(linkptr); - } - + /* XXX not supported yet + * ret = pyrna_prop_CreatePyObject(ptr, prop); */ + ret = NULL; break; - } default: PyErr_Format(PyExc_AttributeError, "RNA Error: unknown type \"%d\" (pyrna_param_to_py)", type); ret = NULL; @@ -1827,11 +1674,6 @@ PyObject *BPY_rna_module( void ) { PointerRNA ptr; -#ifdef USE_MATHUTILS // register mathutils callbacks, ok to run more then once. - mathutils_rna_array_cb_index= Mathutils_RegisterCallback(&mathutils_rna_array_cb); - mathutils_rna_matrix_cb_index= Mathutils_RegisterCallback(&mathutils_rna_matrix_cb); -#endif - /* This can't be set in the pytype struct because some compilers complain */ pyrna_prop_Type.tp_getattro = PyObject_GenericGetAttr; pyrna_prop_Type.tp_setattro = PyObject_GenericSetAttr; @@ -2041,7 +1883,7 @@ PyObject *BPy_BoolProperty(PyObject *self, PyObject *args, PyObject *kw) char *id, *name="", *description=""; int def=0; - if (!PyArg_ParseTupleAndKeywords(args, kw, "s|ssi:BoolProperty", kwlist, &id, &name, &description, &def)) + if (!PyArg_ParseTupleAndKeywords(args, kw, "s|ssi:IntProperty", kwlist, &id, &name, &description, &def)) return NULL; if (PyTuple_Size(args) > 0) { @@ -2055,7 +1897,7 @@ PyObject *BPy_BoolProperty(PyObject *self, PyObject *args, PyObject *kw) Py_RETURN_NONE; } else { PyObject *ret = PyTuple_New(2); - PyTuple_SET_ITEM(ret, 0, PyCObject_FromVoidPtr((void *)BPy_BoolProperty, NULL)); + PyTuple_SET_ITEM(ret, 0, PyCObject_FromVoidPtr((void *)BPy_IntProperty, NULL)); PyTuple_SET_ITEM(ret, 1, kw); Py_INCREF(kw); return ret; diff --git a/source/blender/python/intern/bpy_rna.h b/source/blender/python/intern/bpy_rna.h index d2f01b06336..45614e992c6 100644 --- a/source/blender/python/intern/bpy_rna.h +++ b/source/blender/python/intern/bpy_rna.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: bpy_rna.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/python/intern/bpy_ui.c b/source/blender/python/intern/bpy_ui.c index 088fe436c69..ccc8b2c206a 100644 --- a/source/blender/python/intern/bpy_ui.c +++ b/source/blender/python/intern/bpy_ui.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: bpy_ui.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/python/intern/bpy_ui.h b/source/blender/python/intern/bpy_ui.h index 4182a32d3f0..be5e5e87015 100644 --- a/source/blender/python/intern/bpy_ui.h +++ b/source/blender/python/intern/bpy_ui.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: bpy_ui.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/python/intern/bpy_util.c b/source/blender/python/intern/bpy_util.c index bce73b903c0..6ec01e0c3fc 100644 --- a/source/blender/python/intern/bpy_util.c +++ b/source/blender/python/intern/bpy_util.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: bpy_util.c 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * @@ -171,7 +171,7 @@ void PyObSpit(char *name, PyObject *var) { else { PyObject_Print(var, stderr, 0); fprintf(stderr, " ref:%d ", var->ob_refcnt); - fprintf(stderr, " ptr:%p", (void *)var); + fprintf(stderr, " ptr:%ld", (long)var); fprintf(stderr, " type:"); if(Py_TYPE(var)) diff --git a/source/blender/python/intern/bpy_util.h b/source/blender/python/intern/bpy_util.h index 6429af67eb0..bc87da75de6 100644 --- a/source/blender/python/intern/bpy_util.h +++ b/source/blender/python/intern/bpy_util.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: bpy_util.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/radiosity/CMakeLists.txt b/source/blender/radiosity/CMakeLists.txt new file mode 100644 index 00000000000..e76f7409f99 --- /dev/null +++ b/source/blender/radiosity/CMakeLists.txt @@ -0,0 +1,36 @@ +# $Id$ +# ***** BEGIN GPL LICENSE BLOCK ***** +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software Foundation, +# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# The Original Code is Copyright (C) 2006, Blender Foundation +# All rights reserved. +# +# The Original Code is: all of this file. +# +# Contributor(s): Jacques Beaurain. +# +# ***** END GPL LICENSE BLOCK ***** + +FILE(GLOB SRC intern/source/*.c) + +SET(INC + extern/include ../blenlib ../blenkernel ../makesdna ../editors/include + ../../../intern/guardedalloc ../render/extern/include + ../render/intern/include ../blenloader ../../../extern/glew/include +) + +BLENDERLIB_NOLIST(blender_radiosity "${SRC}" "${INC}") +#env.BlenderLib ( 'blender_radiosity', sources, Split(incs), [], libtype='core', priority=50 ) diff --git a/source/blender/radiosity/Makefile b/source/blender/radiosity/Makefile new file mode 100644 index 00000000000..91a13e2fd57 --- /dev/null +++ b/source/blender/radiosity/Makefile @@ -0,0 +1,34 @@ +# +# $Id$ +# +# ***** BEGIN GPL LICENSE BLOCK ***** +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software Foundation, +# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. +# All rights reserved. +# +# The Original Code is: all of this file. +# +# Contributor(s): none yet. +# +# ***** END GPL LICENSE BLOCK ***** +# +# Makes module object directory and bounces make to subdirectories. + +SOURCEDIR = source/blender/radiosity +DIRS = intern + +include nan_subdirs.mk diff --git a/source/blender/radiosity/SConscript b/source/blender/radiosity/SConscript new file mode 100644 index 00000000000..29854d2ee83 --- /dev/null +++ b/source/blender/radiosity/SConscript @@ -0,0 +1,12 @@ +#!/usr/bin/python +Import ('env') + +sources = env.Glob('intern/source/*.c') + +incs = 'extern/include ../blenlib ../blenkernel ../makesdna ../editors/include' +incs += ' #/intern/guardedalloc ../render/extern/include' +incs += ' ../render/intern/include ../blenloader #/extern/glew/include' + +incs += ' ' + env['BF_OPENGL_INC'] + +env.BlenderLib ( 'bf_radiosity', sources, Split(incs), [], libtype='core', priority=150 ) diff --git a/source/blender/radiosity/extern/include/radio.h b/source/blender/radiosity/extern/include/radio.h new file mode 100644 index 00000000000..e7f23302880 --- /dev/null +++ b/source/blender/radiosity/extern/include/radio.h @@ -0,0 +1,173 @@ +/* *************************************** + + + + radio.h nov/dec 1992 + revised for Blender may 1999 + + $Id$ + + ***** BEGIN GPL LICENSE BLOCK ***** + + This program is free software; you can redistribute it and/or + modify it under the terms of the GNU General Public License + as published by the Free Software Foundation; either version 2 + of the License, or (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software Foundation, + Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + + The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + All rights reserved. + + The Original Code is: all of this file. + + Contributor(s): none yet. + + ***** END GPL LICENSE BLOCK ***** + */ + +#ifndef RADIO_H +#define RADIO_H +#define RADIO_H + +/* type include */ +#include "radio_types.h" + +extern RadGlobal RG; +struct View3D; +struct Scene; + +/* radfactors.c */ +extern float calcStokefactor(RPatch *shoot, RPatch *rp, RNode *rn, float *area); +extern void calcTopfactors(void); +void calcSidefactors(void); +extern void initradiosity(void); +extern void rad_make_hocos(RadView *vw); +extern void hemizbuf(RadView *vw); +extern int makeformfactors(RPatch *shoot); +extern void applyformfactors(RPatch *shoot); +extern RPatch *findshootpatch(void); +extern void setnodeflags(RNode *rn, int flag, int set); +extern void backface_test(RPatch *shoot); +extern void clear_backface_test(void); +extern void progressiverad(void); +extern void minmaxradelem(RNode *rn, float *min, float *max); +extern void minmaxradelemfilt(RNode *rn, float *min, float *max, float *errmin, float *errmax); +extern void subdivideshootElements(int it); +extern void subdivideshootPatches(int it); +extern void inithemiwindows(void); +extern void closehemiwindows(void); +void rad_init_energy(void); + +/* radio.c */ +void freeAllRad(struct Scene *scene); +int rad_phase(void); +void rad_status_str(char *str); +void rad_printstatus(void); +void rad_setlimits(struct Scene *scene); +void set_radglobal(struct Scene *scene); +void add_radio(struct Scene *scene); +void delete_radio(struct Scene *scene); +int rad_go(struct Scene *scene); +void rad_subdivshootpatch(struct Scene *scene); +void rad_subdivshootelem(struct Scene *scene); +void rad_limit_subdivide(struct Scene *scene); + +/* radnode.c */ +extern void setnodelimit(float limit); +extern float *mallocVert(void); +extern float *callocVert(void); +extern void freeVert(float *vert); +extern int totalRadVert(void); +extern RNode *mallocNode(void); +extern RNode *callocNode(void); +extern void freeNode(RNode *node); +extern void freeNode_recurs(RNode *node); +extern RPatch *mallocPatch(void); +extern RPatch *callocPatch(void); +extern void freePatch(RPatch *patch); +extern void replaceAllNode(RNode *, RNode *); +extern void replaceAllNodeInv(RNode *neighb, RNode *old); +extern void replaceAllNodeUp(RNode *neighb, RNode *old); +extern void replaceTestNode(RNode *, RNode **, RNode *, int , float *); +extern void free_fastAll(void); + +/* radnode.c */ +extern void start_fastmalloc(char *str); +extern int setvertexpointersNode(RNode *neighb, RNode *node, int level, float **v1, float **v2); +extern float edlen(float *v1, float *v2); +extern void deleteNodes(RNode *node); +extern void subdivideTriNode(RNode *node, RNode *edge); +extern void subdivideNode(RNode *node, RNode *edge); +extern int comparelevel(RNode *node, RNode *nb, int level); + +/* radpreprocess.c */ +extern void splitconnected(void); +extern int vergedge(const void *v1,const void *v2); +extern void addedge(float *v1, float *v2, EdSort *es); +extern void setedgepointers(void); +extern void rad_collect_meshes(struct Scene *scene, struct View3D *v3d); +extern void countelem(RNode *rn); +extern void countglobaldata(void); +extern void addelem(RNode ***el, RNode *rn, RPatch *rp); +extern void makeGlobalElemArray(void); +extern void remakeGlobaldata(void); +extern void splitpatch(RPatch *old); +extern void addpatch(RPatch *old, RNode *rn); +extern void converttopatches(void); +extern void make_elements(void); +extern void subdividelamps(void); +extern void maxsizePatches(void); +extern void subdiv_elements(void); + +/* radpostprocess.c */ +void addaccu(register char *z, register char *t); +void addaccuweight(register char *z, register char *t, int w); +void triaweight(Face *face, int *w1, int *w2, int *w3); +void init_face_tab(void); +Face *addface(void); +Face *makeface(float *v1, float *v2, float *v3, float *v4, RNode *rn); +void anchorQuadface(RNode *rn, float *v1, float *v2, float *v3, float *v4, int flag); +void anchorTriface(RNode *rn, float *v1, float *v2, float *v3, int flag); +float *findmiddlevertex(RNode *node, RNode *nb, float *v1, float *v2); +void make_face_tab(void); +void filterFaces(void); +void calcfiltrad(RNode *rn, float *cd); +void filterNodes(void); +void removeEqualNodes(short limit); +void rad_addmesh(struct Scene *scene); +void rad_replacemesh(struct Scene *scene); + +/* raddisplay.c */ +extern char calculatecolor(float col); +extern void make_node_display(void); +extern void drawnodeWire(RNode *rn); +extern void drawsingnodeWire(RNode *rn); +extern void drawnodeSolid(RNode *rn); +extern void drawnodeGour(RNode *rn); +extern void drawpatch(RPatch *patch, unsigned int col); +extern void drawfaceGour(Face *face); +extern void drawfaceSolid(Face *face); +extern void drawfaceWire(Face *face); +extern void drawsquare(float *cent, float size, short cox, short coy); +extern void drawlimits(void); +extern void setcolNode(RNode *rn, unsigned int *col); +extern void pseudoAmb(void); +extern void rad_forcedraw(void); +extern void drawpatch_ext(RPatch *patch, unsigned int col); +extern void RAD_drawall(int depth_is_on); + +/* radrender.c */ +struct Render; +extern void do_radio_render(struct Render *re); +void end_radio_render(void); + +#endif /* RADIO_H */ + diff --git a/source/blender/radiosity/extern/include/radio_types.h b/source/blender/radiosity/extern/include/radio_types.h new file mode 100644 index 00000000000..5a218ee71be --- /dev/null +++ b/source/blender/radiosity/extern/include/radio_types.h @@ -0,0 +1,168 @@ +/* + * radio_types.h + * + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ + +/* #include "misc_util.h" */ /* for listbase...*/ + + +#ifndef RADIO_TYPES_H +#define RADIO_TYPES_H + +#include "DNA_listBase.h" +#include "DNA_material_types.h" + +struct Render; +struct CustomData; + +#define PI M_PI +#define RAD_MAXFACETAB 1024 +#define RAD_NEXTFACE(a) if( ((a) & 1023)==0 ) face= RG.facebase[(a)>>10]; else face++; + +/* RG.phase */ +#define RAD_SHOOTE 1 +#define RAD_SHOOTP 2 +#define RAD_SOLVE 3 + +typedef struct RadView { + float cam[3], tar[3], up[3]; + float wx1, wx2, wy1, wy2; + float mynear, myfar; + float viewmat[4][4], winmat[4][4]; + unsigned int *rect, *rectz; + short rectx, recty; + int wid; + +} RadView; + +/* rn->f */ +#define RAD_PATCH 1 +#define RAD_SHOOT 2 +#define RAD_SUBDIV 4 +#define RAD_BACKFACE 8 +#define RAD_TWOSIDED 16 + + +typedef struct RNode { /* length: 104 */ + struct RNode *down1, *down2, *up; + struct RNode *ed1, *ed2, *ed3, *ed4; + struct RPatch *par; + + char lev1, lev2, lev3, lev4; /* edgelevels */ + short type; /* type: 4==QUAD, 3==TRIA */ + short f; + float *v1, *v2, *v3, *v4; + float totrad[3], area; + + unsigned int col; + int orig; /* index in custom face data */ +} RNode; + + +typedef struct Face { /* length: 52 */ + float *v1, *v2, *v3, *v4; + unsigned int col, matindex; + int orig; /* index in custom face data */ +} Face; + +/* rp->f1 */ +#define RAD_NO_SPLIT 1 + +typedef struct RPatch { + struct RPatch *next, *prev; + RNode *first; /* first node==patch */ + + struct Object *from; + + int type; /* 3: TRIA, 4: QUAD */ + short f, f1; /* flags f: if node, only for subdiv */ + + float ref[3], emit[3], unshot[3]; + float cent[3], norm[3]; + float area; + int matindex; + +} RPatch; + + +typedef struct VeNoCo { /* needed for splitconnected */ + struct VeNoCo *next; + float *v; + float *n; + float *col; + int flag; +} VeNoCo; + + +typedef struct EdSort { /* sort edges */ + float *v1, *v2; + RNode *node; + int nr; +} EdSort; + +typedef struct { + struct Radio *radio; + unsigned int *hemibuf; + struct ListBase patchbase; + int totpatch, totelem, totvert, totlamp; + RNode **elem; /* global array with all pointers */ + VeNoCo *verts; /* temporal vertices from patches */ + float *formfactors; /* 1 factor per element */ + float *topfactors, *sidefactors; /* LUT for delta's */ + int *index; /* LUT for above LUT */ + Face **facebase; + int totface; + float min[3], max[3], size[3], cent[3]; /* world */ + float maxsize, totenergy; + float patchmin, patchmax; + float elemmin, elemmax; + float radfactor, lostenergy, igamma; /* radfac is in button, radfactor is calculated */ + int phase; + struct Render *re; /* for calling hemizbuf correctly */ + /* to preserve materials as used before, max 16 */ + Material *matar[MAXMAT]; + int totmat; + + /* for preserving face data */ + int mfdatatot; + struct CustomData *mfdata; + struct RNode **mfdatanodes; + + /* this part is a copy of struct Radio */ + short hemires, maxiter; + short drawtype, flag; /* bit 0 en 1: show limits */ + short subshootp, subshoote, nodelim, maxsublamp; + int maxnode; + float convergence; + float radfac, gamma; /* for display */ + +} RadGlobal; + +#endif /* radio_types.h */ + diff --git a/source/blender/radiosity/intern/Makefile b/source/blender/radiosity/intern/Makefile new file mode 100644 index 00000000000..456b51cc56e --- /dev/null +++ b/source/blender/radiosity/intern/Makefile @@ -0,0 +1,34 @@ +# +# $Id$ +# +# ***** BEGIN GPL LICENSE BLOCK ***** +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software Foundation, +# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. +# All rights reserved. +# +# The Original Code is: all of this file. +# +# Contributor(s): none yet. +# +# ***** END GPL LICENSE BLOCK ***** +# +# Makes module object directory and bounces make to subdirectories. + +SOURCEDIR = source/blender/radiosity/intern +DIRS = source + +include nan_subdirs.mk diff --git a/source/blender/radiosity/intern/source/Makefile b/source/blender/radiosity/intern/source/Makefile new file mode 100644 index 00000000000..44b38de9bae --- /dev/null +++ b/source/blender/radiosity/intern/source/Makefile @@ -0,0 +1,55 @@ +# +# $Id$ +# +# ***** BEGIN GPL LICENSE BLOCK ***** +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software Foundation, +# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. +# All rights reserved. +# +# The Original Code is: all of this file. +# +# Contributor(s): none yet. +# +# ***** END GPL LICENSE BLOCK ***** +# +# radiosity uses the render lib +# + +LIBNAME = radiosity +DIR = $(OCGDIR)/blender/$(LIBNAME) + +include nan_compile.mk + +CFLAGS += $(LEVEL_1_C_WARNINGS) + +CPPFLAGS += -I$(NAN_GLEW)/include +CPPFLAGS += -I$(OPENGL_HEADERS) + +# not very neat.... +CPPFLAGS += -I../../../blenkernel +CPPFLAGS += -I../../../blenlib +CPPFLAGS += -I../../../makesdna +CPPFLAGS += -I../../../imbuf +CPPFLAGS += -I../../../ +CPPFLAGS += -I../../../blenloader +CPPFLAGS += -I$(NAN_GUARDEDALLOC)/include + +# first /include is my own includes, second are the external includes +# third is the external interface. there should be a nicer way to say this +CPPFLAGS += -I../include -I../../../editors/include -I../../extern/include +CPPFLAGS += -I../../../render/extern/include +CPPFLAGS += -I../../../render/intern/include diff --git a/source/blender/radiosity/intern/source/raddisplay.c b/source/blender/radiosity/intern/source/raddisplay.c new file mode 100644 index 00000000000..ab9e8eedc28 --- /dev/null +++ b/source/blender/radiosity/intern/source/raddisplay.c @@ -0,0 +1,477 @@ +/* *************************************** + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + + + + raddisplay.c nov/dec 1992 + may 1999 + + - drawing + - color calculation for display during solving + + $Id$ + + *************************************** */ + +#include <stdlib.h> +#include <math.h> + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +#include "BLI_blenlib.h" + +#include "DNA_radio_types.h" +#include "DNA_screen_types.h" +#include "DNA_space_types.h" +#include "DNA_view3d_types.h" + +#include "BKE_global.h" +#include "BKE_main.h" + +#include "BIF_gl.h" + +#include "radio.h" + +/* cpack has to be endian-insensitive! (old irisgl function) */ +#define cpack(x) glColor3ub( ((x)&0xFF), (((x)>>8)&0xFF), (((x)>>16)&0xFF) ) + +char calculatecolor(float col) +{ + int b; + + if(RG.gamma==1.0) { + b= RG.radfactor*col; + } + else if(RG.gamma==2.0) { + b= RG.radfactor*sqrt(col); + } + else { + b= RG.radfactor*pow(col, RG.igamma); + } + + if(b>255) b=255; + return b; +} + +void make_node_display() +{ + RNode *rn, **el; + int a; + char *charcol; + + RG.igamma= 1.0/RG.gamma; + RG.radfactor= RG.radfac*pow(64*64, RG.igamma); + + el= RG.elem; + for(a=RG.totelem; a>0; a--, el++) { + rn= *el; + charcol= (char *)&( rn->col ); + + charcol[3]= calculatecolor(rn->totrad[0]); + charcol[2]= calculatecolor(rn->totrad[1]); + charcol[1]= calculatecolor(rn->totrad[2]); + + /* gouraudcolor */ + *(rn->v1+3)= 0; + *(rn->v2+3)= 0; + *(rn->v3+3)= 0; + if(rn->v4) *(rn->v4+3)= 0; + } + + el= RG.elem; + for(a=RG.totelem; a>0; a--, el++) { + rn= *el; + addaccuweight( (char *)&(rn->col), (char *)(rn->v1+3), 16 ); + addaccuweight( (char *)&(rn->col), (char *)(rn->v2+3), 16 ); + addaccuweight( (char *)&(rn->col), (char *)(rn->v3+3), 16 ); + if(rn->v4) addaccuweight( (char *)&(rn->col), (char *)(rn->v4+3), 16 ); + } +} + +void drawnodeWire(RNode *rn) +{ + + if(rn->down1) { + drawnodeWire(rn->down1); + drawnodeWire(rn->down2); + } + else { + glBegin(GL_LINE_LOOP); + glVertex3fv(rn->v1); + glVertex3fv(rn->v2); + glVertex3fv(rn->v3); + if(rn->type==4) glVertex3fv(rn->v4); + glEnd(); + } +} + +void drawsingnodeWire(RNode *rn) +{ + + glBegin(GL_LINE_LOOP); + glVertex3fv(rn->v1); + glVertex3fv(rn->v2); + glVertex3fv(rn->v3); + if(rn->type==4) glVertex3fv(rn->v4); + glEnd(); +} + +void drawnodeSolid(RNode *rn) +{ + char *cp; + + if(rn->down1) { + drawnodeSolid(rn->down1); + drawnodeSolid(rn->down2); + } + else { + cp= (char *)&rn->col; + glColor3ub(cp[3], cp[2], cp[1]); + glBegin(GL_POLYGON); + glVertex3fv(rn->v1); + glVertex3fv(rn->v2); + glVertex3fv(rn->v3); + if(rn->type==4) glVertex3fv(rn->v4); + glEnd(); + } +} + +void drawnodeGour(RNode *rn) +{ + char *cp; + + if(rn->down1) { + drawnodeGour(rn->down1); + drawnodeGour(rn->down2); + } + else { + glBegin(GL_POLYGON); + cp= (char *)(rn->v1+3); + glColor3ub(cp[3], cp[2], cp[1]); + glVertex3fv(rn->v1); + + cp= (char *)(rn->v2+3); + glColor3ub(cp[3], cp[2], cp[1]); + glVertex3fv(rn->v2); + + cp= (char *)(rn->v3+3); + glColor3ub(cp[3], cp[2], cp[1]); + glVertex3fv(rn->v3); + + if(rn->type==4) { + cp= (char *)(rn->v4+3); + glColor3ub(cp[3], cp[2], cp[1]); + glVertex3fv(rn->v4); + } + glEnd(); + } +} + +void drawpatch_ext(RPatch *patch, unsigned int col) +{ + ScrArea *sa, *oldsa; + View3D *v3d; + glDrawBuffer(GL_FRONT); + + return; // XXX + + cpack(col); + + oldsa= NULL; // XXX curarea; + +// sa= G.curscreen->areabase.first; + while(sa) { + if (sa->spacetype==SPACE_VIEW3D) { + v3d= sa->spacedata.first; + + /* use mywinget() here: otherwise it draws in header */ +// XXX if(sa->win != mywinget()) areawinset(sa->win); +// XXX persp(PERSP_VIEW); + if(v3d->zbuf) glDisable(GL_DEPTH_TEST); + drawnodeWire(patch->first); + if(v3d->zbuf) glEnable(GL_DEPTH_TEST); // pretty useless? + } + sa= sa->next; + } + +// XXX if(oldsa && oldsa!=curarea) areawinset(oldsa->win); + + glFlush(); + glDrawBuffer(GL_BACK); +} + + +void drawfaceGour(Face *face) +{ + char *cp; + + glBegin(GL_POLYGON); + cp= (char *)(face->v1+3); + glColor3ub(cp[3], cp[2], cp[1]); + glVertex3fv(face->v1); + + cp= (char *)(face->v2+3); + glColor3ub(cp[3], cp[2], cp[1]); + glVertex3fv(face->v2); + + cp= (char *)(face->v3+3); + glColor3ub(cp[3], cp[2], cp[1]); + glVertex3fv(face->v3); + + if(face->v4) { + cp= (char *)(face->v4+3); + glColor3ub(cp[3], cp[2], cp[1]); + glVertex3fv(face->v4); + } + glEnd(); + +} + +void drawfaceSolid(Face *face) +{ + char *cp; + + cp= (char *)&face->col; + glColor3ub(cp[3], cp[2], cp[1]); + + glBegin(GL_POLYGON); + glVertex3fv(face->v1); + glVertex3fv(face->v2); + glVertex3fv(face->v3); + if(face->v4) { + glVertex3fv(face->v4); + } + glEnd(); + +} + +void drawfaceWire(Face *face) +{ + char *cp; + + cp= (char *)&face->col; + glColor3ub(cp[3], cp[2], cp[1]); + + glBegin(GL_LINE_LOOP); + glVertex3fv(face->v1); + glVertex3fv(face->v2); + glVertex3fv(face->v3); + if(face->v4) { + glVertex3fv(face->v4); + } + glEnd(); + +} + +void drawsquare(float *cent, float size, short cox, short coy) +{ + float vec[3]; + + vec[0]= cent[0]; + vec[1]= cent[1]; + vec[2]= cent[2]; + + glBegin(GL_LINE_LOOP); + vec[cox]+= .5*size; + vec[coy]+= .5*size; + glVertex3fv(vec); + vec[coy]-= size; + glVertex3fv(vec); + vec[cox]-= size; + glVertex3fv(vec); + vec[coy]+= size; + glVertex3fv(vec); + glEnd(); +} + +void drawlimits() +{ + /* center around cent */ + short cox=0, coy=1; + + if((RG.flag & (RAD_SHOWLIMITS|RAD_SHOWZ))==RAD_SHOWZ) coy= 2; + if((RG.flag & (RAD_SHOWLIMITS|RAD_SHOWZ))==(RAD_SHOWLIMITS|RAD_SHOWZ)) { + cox= 1; + coy= 2; + } + + cpack(0); + drawsquare(RG.cent, sqrt(RG.patchmax), cox, coy); + drawsquare(RG.cent, sqrt(RG.patchmin), cox, coy); + + drawsquare(RG.cent, sqrt(RG.elemmax), cox, coy); + drawsquare(RG.cent, sqrt(RG.elemmin), cox, coy); + + cpack(0xFFFFFF); + drawsquare(RG.cent, sqrt(RG.patchmax), cox, coy); + drawsquare(RG.cent, sqrt(RG.patchmin), cox, coy); + cpack(0xFFFF00); + drawsquare(RG.cent, sqrt(RG.elemmax), cox, coy); + drawsquare(RG.cent, sqrt(RG.elemmin), cox, coy); + +} + +void setcolNode(RNode *rn, unsigned int *col) +{ + + if(rn->down1) { + setcolNode(rn->down1, col); + setcolNode(rn->down2, col); + } + rn->col= *col; + + *((unsigned int *)rn->v1+3)= *col; + *((unsigned int *)rn->v2+3)= *col; + *((unsigned int *)rn->v3+3)= *col; + if(rn->v4) *((unsigned int *)rn->v4+3)= *col; +} + +void pseudoAmb() +{ + RPatch *rp; + float fac; + char col[4]; + + /* sets pseudo ambient color in the nodes */ + + rp= RG.patchbase.first; + while(rp) { + + if(rp->emit[0]!=0.0 || rp->emit[1]!=0.0 || rp->emit[2]!=0.0) { + col[1]= col[2]= col[3]= 255; + } + else { + fac= rp->norm[0]+ rp->norm[1]+ rp->norm[2]; + fac= 225.0*(3+fac)/6.0; + + col[3]= fac*rp->ref[0]; + col[2]= fac*rp->ref[1]; + col[1]= fac*rp->ref[2]; + } + + setcolNode(rp->first, (unsigned int *)col); + + rp= rp->next; + } +} + +void RAD_drawall(int depth_is_on) +{ + /* displays elements or faces */ + Face *face = NULL; + RNode **el; + RPatch *rp; + int a; + + if(!depth_is_on) { + glEnable(GL_DEPTH_TEST); + glClearDepth(1.0); glClear(GL_DEPTH_BUFFER_BIT); + } + + if(RG.totface) { + if(RG.drawtype==RAD_GOURAUD) { + glShadeModel(GL_SMOOTH); + for(a=0; a<RG.totface; a++) { + RAD_NEXTFACE(a); + + drawfaceGour(face); + } + } + else if(RG.drawtype==RAD_SOLID) { + for(a=0; a<RG.totface; a++) { + RAD_NEXTFACE(a); + + drawfaceSolid(face); + } + } + else { + cpack(0); + rp= RG.patchbase.first; + while(rp) { + drawsingnodeWire(rp->first); + rp= rp->next; + } + } + } + else { + el= RG.elem; + if(RG.drawtype==RAD_GOURAUD) { + glShadeModel(GL_SMOOTH); + for(a=RG.totelem; a>0; a--, el++) { + drawnodeGour(*el); + } + } + else if(RG.drawtype==RAD_SOLID) { + for(a=RG.totelem; a>0; a--, el++) { + drawnodeSolid(*el); + } + } + else { + cpack(0); + for(a=RG.totelem; a>0; a--, el++) { + drawnodeWire(*el); + } + } + } + glShadeModel(GL_FLAT); + + if(RG.totpatch) { + if(RG.flag & (RAD_SHOWLIMITS|RAD_SHOWZ)) { + if(depth_is_on) glDisable(GL_DEPTH_TEST); + drawlimits(); + if(depth_is_on) glEnable(GL_DEPTH_TEST); + } + } + if(!depth_is_on) { + glDisable(GL_DEPTH_TEST); + } +} + +void rad_forcedraw() +{ + ScrArea *sa, *oldsa; + + return; // XXX + + oldsa= NULL; // XXX curarea; + +/// sa= G.curscreen->areabase.first; + while(sa) { + if (sa->spacetype==SPACE_VIEW3D) { + /* use mywinget() here: othwerwise it draws in header */ +// XXX if(sa->win != mywinget()) areawinset(sa->win); +// XXX scrarea_do_windraw(sa); + } + sa= sa->next; + } +// XXX screen_swapbuffers(); + +// XXX if(oldsa && oldsa!=curarea) areawinset(oldsa->win); +} + diff --git a/source/blender/radiosity/intern/source/radfactors.c b/source/blender/radiosity/intern/source/radfactors.c new file mode 100644 index 00000000000..b87473dd811 --- /dev/null +++ b/source/blender/radiosity/intern/source/radfactors.c @@ -0,0 +1,939 @@ +/* *************************************** + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + + + + formfactors.c nov/dec 1992 + + $Id$ + + *************************************** */ + +#include <stdlib.h> +#include <string.h> +#include <math.h> + +#include "MEM_guardedalloc.h" + +#include "BLI_blenlib.h" +#include "BLI_arithb.h" +#include "BLI_rand.h" + +#include "BKE_utildefines.h" +#include "BKE_global.h" +#include "BKE_main.h" + +#include "radio.h" +#include "RE_render_ext.h" /* for `RE_zbufferall_radio and RE_zbufferall_radio */ + +/* locals */ +static void rad_setmatrices(RadView *vw); +static void clearsubflagelem(RNode *rn); +static void setsubflagelem(RNode *rn); + +RadView hemitop, hemiside; + +float calcStokefactor(RPatch *shoot, RPatch *rp, RNode *rn, float *area) +{ + float tvec[3], fac; + float vec[4][3]; /* vectors of shoot->cent to vertices rp */ + float cross[4][3]; /* cross products of this */ + float rad[4]; /* anlgles between vecs */ + + /* test for direction */ + VecSubf(tvec, shoot->cent, rp->cent); + if( tvec[0]*shoot->norm[0]+ tvec[1]*shoot->norm[1]+ tvec[2]*shoot->norm[2]>0.0) + return 0.0; + + if(rp->type==4) { + + /* corner vectors */ + VecSubf(vec[0], shoot->cent, rn->v1); + VecSubf(vec[1], shoot->cent, rn->v2); + VecSubf(vec[2], shoot->cent, rn->v3); + VecSubf(vec[3], shoot->cent, rn->v4); + + Normalize(vec[0]); + Normalize(vec[1]); + Normalize(vec[2]); + Normalize(vec[3]); + + /* cross product */ + Crossf(cross[0], vec[0], vec[1]); + Crossf(cross[1], vec[1], vec[2]); + Crossf(cross[2], vec[2], vec[3]); + Crossf(cross[3], vec[3], vec[0]); + Normalize(cross[0]); + Normalize(cross[1]); + Normalize(cross[2]); + Normalize(cross[3]); + + /* angles */ + rad[0]= vec[0][0]*vec[1][0]+ vec[0][1]*vec[1][1]+ vec[0][2]*vec[1][2]; + rad[1]= vec[1][0]*vec[2][0]+ vec[1][1]*vec[2][1]+ vec[1][2]*vec[2][2]; + rad[2]= vec[2][0]*vec[3][0]+ vec[2][1]*vec[3][1]+ vec[2][2]*vec[3][2]; + rad[3]= vec[3][0]*vec[0][0]+ vec[3][1]*vec[0][1]+ vec[3][2]*vec[0][2]; + + rad[0]= acos(rad[0]); + rad[1]= acos(rad[1]); + rad[2]= acos(rad[2]); + rad[3]= acos(rad[3]); + + /* Stoke formula */ + VecMulf(cross[0], rad[0]); + VecMulf(cross[1], rad[1]); + VecMulf(cross[2], rad[2]); + VecMulf(cross[3], rad[3]); + + VECCOPY(tvec, shoot->norm); + fac= tvec[0]*cross[0][0]+ tvec[1]*cross[0][1]+ tvec[2]*cross[0][2]; + fac+= tvec[0]*cross[1][0]+ tvec[1]*cross[1][1]+ tvec[2]*cross[1][2]; + fac+= tvec[0]*cross[2][0]+ tvec[1]*cross[2][1]+ tvec[2]*cross[2][2]; + fac+= tvec[0]*cross[3][0]+ tvec[1]*cross[3][1]+ tvec[2]*cross[3][2]; + } + else { + /* corner vectors */ + VecSubf(vec[0], shoot->cent, rn->v1); + VecSubf(vec[1], shoot->cent, rn->v2); + VecSubf(vec[2], shoot->cent, rn->v3); + + Normalize(vec[0]); + Normalize(vec[1]); + Normalize(vec[2]); + + /* cross product */ + Crossf(cross[0], vec[0], vec[1]); + Crossf(cross[1], vec[1], vec[2]); + Crossf(cross[2], vec[2], vec[0]); + Normalize(cross[0]); + Normalize(cross[1]); + Normalize(cross[2]); + + /* angles */ + rad[0]= vec[0][0]*vec[1][0]+ vec[0][1]*vec[1][1]+ vec[0][2]*vec[1][2]; + rad[1]= vec[1][0]*vec[2][0]+ vec[1][1]*vec[2][1]+ vec[1][2]*vec[2][2]; + rad[2]= vec[2][0]*vec[0][0]+ vec[2][1]*vec[0][1]+ vec[2][2]*vec[0][2]; + + rad[0]= acos(rad[0]); + rad[1]= acos(rad[1]); + rad[2]= acos(rad[2]); + + /* Stoke formula */ + VecMulf(cross[0], rad[0]); + VecMulf(cross[1], rad[1]); + VecMulf(cross[2], rad[2]); + + VECCOPY(tvec, shoot->norm); + fac= tvec[0]*cross[0][0]+ tvec[1]*cross[0][1]+ tvec[2]*cross[0][2]; + fac+= tvec[0]*cross[1][0]+ tvec[1]*cross[1][1]+ tvec[2]*cross[1][2]; + fac+= tvec[0]*cross[2][0]+ tvec[1]*cross[2][1]+ tvec[2]*cross[2][2]; + } + + *area= -fac/(2.0*PI); + return (*area * (shoot->area/rn->area)); +} + + +void calcTopfactors() +{ + float xsq , ysq, xysq; + float n; + float *fp; + int a, b, hres; + + fp = RG.topfactors; + hres= RG.hemires/2; + n= hres; + + for (a=0; a<hres; a++) { + + ysq= (n- ((float)a+0.5))/n; + ysq*= ysq; + + for ( b=0 ; b<hres ; b++ ) { + + xsq= ( n-((float)b+ 0.5) )/n; + xsq*= xsq; + xysq= xsq+ ysq+ 1.0 ; + xysq*= xysq; + + *fp++ = 1.0/(xysq* PI* n*n); + } + } + +} + +void calcSidefactors() +{ + float xsq , ysq, xysq; + float n, y; + float *fp; + int a, b, hres; + + fp = RG.sidefactors; + hres= RG.hemires/2; + n= hres; + + for (a=0; a<hres; a++) { + + y= (n- ((float)a+0.5))/n; + ysq= y*y; + + for ( b=0 ; b<hres ; b++ ) { + + xsq= ( n-((float)b+ 0.5) )/n; + xsq*= xsq; + xysq= xsq+ ysq+ 1.0 ; + xysq*= xysq; + + *fp++ = y/(xysq* PI* n*n); + } + } + +} + + +void initradiosity() +{ + /* allocates and makes LUTs for top/side factors */ + /* allocates and makes index array */ + int a, hres2; + + if(RG.topfactors) MEM_freeN(RG.topfactors); + if(RG.sidefactors) MEM_freeN(RG.sidefactors); + if(RG.index) MEM_freeN(RG.index); + + RG.topfactors= MEM_callocN(RG.hemires*RG.hemires, "initradiosity"); + calcTopfactors(); + RG.sidefactors= MEM_callocN(RG.hemires*RG.hemires, "initradiosity1"); + calcSidefactors(); + + RG.index= MEM_callocN(4*RG.hemires, "initradiosity3"); + hres2= RG.hemires/2; + for(a=0; a<RG.hemires; a++) { + RG.index[a]= a<hres2 ? a: (hres2-1-( a % hres2 )); + } + +} + +void rad_make_hocos(RadView *vw) +{ + /* float hoco[4]; */ + /* int a; */ + + /* for(a=0; a< R.totvert;a++) { */ + /* projectvert(vec, ver->ho); */ + /* ver->clip = testclip(ver->ho); */ +/* */ + /* } */ +} + +static void rad_setmatrices(RadView *vw) /* for hemi's */ +{ + float up1[3], len, twist; + + i_lookat(vw->cam[0], vw->cam[1], vw->cam[2], vw->tar[0], vw->tar[1], vw->tar[2], 0, vw->viewmat); + up1[0] = vw->viewmat[0][0]*vw->up[0] + vw->viewmat[1][0]*vw->up[1] + vw->viewmat[2][0]*vw->up[2]; + up1[1] = vw->viewmat[0][1]*vw->up[0] + vw->viewmat[1][1]*vw->up[1] + vw->viewmat[2][1]*vw->up[2]; + up1[2] = vw->viewmat[0][2]*vw->up[0] + vw->viewmat[1][2]*vw->up[1] + vw->viewmat[2][2]*vw->up[2]; + + len= up1[0]*up1[0]+up1[1]*up1[1]; + if(len>0.0) { + twist= -atan2(up1[0], up1[1]); + } + else twist= 0.0; + + i_lookat(vw->cam[0], vw->cam[1], vw->cam[2], vw->tar[0], vw->tar[1], vw->tar[2], (180.0*twist/M_PI), vw->viewmat); + + /* window matrix was set in inithemiwindows */ + +} + + +void hemizbuf(RadView *vw) +{ + float *factors; + unsigned int *rz; + int a, b, inda, hres; + + rad_setmatrices(vw); + RE_zbufferall_radio(vw, RG.elem, RG.totelem, RG.re); /* Render for when we got renderfaces */ + + /* count factors */ + if(vw->recty==vw->rectx) factors= RG.topfactors; + else factors= RG.sidefactors; + hres= RG.hemires/2; + + rz= vw->rect; + for(a=0; a<vw->recty; a++) { + inda= hres*RG.index[a]; + for(b=0; b<vw->rectx; b++, rz++) { + if(*rz<RG.totelem) { + RG.formfactors[*rz]+= factors[inda+RG.index[b]]; + } + } + } +} + +int makeformfactors(RPatch *shoot) +{ + RNode **re; + float len, vec[3], up[3], side[3], tar[5][3], *fp; + int a=0, overfl; + + if(RG.totelem==0) return 0; + + memset(RG.formfactors, 0, 4*RG.totelem); + + /* set up hemiview */ + /* first: random upvector */ + do { + a++; + vec[0]= (float)BLI_drand(); + vec[1]= (float)BLI_drand(); + vec[2]= (float)BLI_drand(); + Crossf(up, shoot->norm, vec); + len= Normalize(up); + /* this safety for input normals that are zero or illegal sized */ + if(a>3) return 0; + } while(len==0.0 || len>1.0); + + VECCOPY(hemitop.up, up); + VECCOPY(hemiside.up, shoot->norm); + + Crossf(side, shoot->norm, up); + + /* five targets */ + VecAddf(tar[0], shoot->cent, shoot->norm); + VecAddf(tar[1], shoot->cent, up); + VecSubf(tar[2], shoot->cent, up); + VecAddf(tar[3], shoot->cent, side); + VecSubf(tar[4], shoot->cent, side); + + /* camera */ + VECCOPY(hemiside.cam, shoot->cent); + VECCOPY(hemitop.cam, shoot->cent); + + /* do it! */ + VECCOPY(hemitop.tar, tar[0]); + hemizbuf(&hemitop); + + for(a=1; a<5; a++) { + VECCOPY(hemiside.tar, tar[a]); + hemizbuf(&hemiside); + } + + /* convert factors to real radiosity */ + re= RG.elem; + fp= RG.formfactors; + + overfl= 0; + for(a= RG.totelem; a>0; a--, re++, fp++) { + + if(*fp!=0.0) { + + *fp *= shoot->area/(*re)->area; + + if(*fp>1.0) { + overfl= 1; + *fp= 1.0001; + } + } + } + + if(overfl) { + if(shoot->first->down1) { + splitpatch(shoot); + return 0; + } + } + + return 1; +} + +void applyformfactors(RPatch *shoot) +{ + RPatch *rp; + RNode **el, *rn; + float *fp, *ref, unr, ung, unb, r, g, b, w; + int a; + + unr= shoot->unshot[0]; + ung= shoot->unshot[1]; + unb= shoot->unshot[2]; + + fp= RG.formfactors; + el= RG.elem; + for(a=0; a<RG.totelem; a++, el++, fp++) { + rn= *el; + if(*fp!= 0.0) { + rp= rn->par; + ref= rp->ref; + + r= (*fp)*unr*ref[0]; + g= (*fp)*ung*ref[1]; + b= (*fp)*unb*ref[2]; + + w= rn->area/rp->area; + rn->totrad[0]+= r; + rn->totrad[1]+= g; + rn->totrad[2]+= b; + + rp->unshot[0]+= w*r; + rp->unshot[1]+= w*g; + rp->unshot[2]+= w*b; + } + } + + shoot->unshot[0]= shoot->unshot[1]= shoot->unshot[2]= 0.0; +} + +RPatch *findshootpatch() +{ + RPatch *rp, *shoot; + float energy, maxenergy; + + shoot= 0; + maxenergy= 0.0; + rp= RG.patchbase.first; + while(rp) { + energy= rp->unshot[0]*rp->area; + energy+= rp->unshot[1]*rp->area; + energy+= rp->unshot[2]*rp->area; + + if(energy>maxenergy) { + shoot= rp; + maxenergy= energy; + } + rp= rp->next; + } + + if(shoot) { + maxenergy/= RG.totenergy; + if(maxenergy<RG.convergence) return 0; + } + + return shoot; +} + +void setnodeflags(RNode *rn, int flag, int set) +{ + + if(rn->down1) { + setnodeflags(rn->down1, flag, set); + setnodeflags(rn->down2, flag, set); + } + else { + if(set) rn->f |= flag; + else rn->f &= ~flag; + } +} + +void backface_test(RPatch *shoot) +{ + RPatch *rp; + float tvec[3]; + + rp= RG.patchbase.first; + while(rp) { + if(rp!=shoot) { + + VecSubf(tvec, shoot->cent, rp->cent); + if( tvec[0]*rp->norm[0]+ tvec[1]*rp->norm[1]+ tvec[2]*rp->norm[2]<0.0) { + setnodeflags(rp->first, RAD_BACKFACE, 1); + } + } + rp= rp->next; + } +} + +void clear_backface_test() +{ + RNode **re; + int a; + + re= RG.elem; + for(a= RG.totelem-1; a>=0; a--, re++) { + (*re)->f &= ~RAD_BACKFACE; + } + +} + +void rad_init_energy() +{ + /* call before shooting */ + /* keep patches and elements, clear all data */ + RNode **el, *rn; + RPatch *rp; + int a; + + el= RG.elem; + for(a=RG.totelem; a>0; a--, el++) { + rn= *el; + VECCOPY(rn->totrad, rn->par->emit); + } + + RG.totenergy= 0.0; + rp= RG.patchbase.first; + while(rp) { + VECCOPY(rp->unshot, rp->emit); + + RG.totenergy+= rp->unshot[0]*rp->area; + RG.totenergy+= rp->unshot[1]*rp->area; + RG.totenergy+= rp->unshot[2]*rp->area; + + rp->f= 0; + + rp= rp->next; + } +} + +void progressiverad() +{ + RPatch *shoot; + float unshot[3]; + int it= 0; + + rad_printstatus(); + rad_init_energy(); + + shoot=findshootpatch(); + + while( shoot ) { + + setnodeflags(shoot->first, RAD_SHOOT, 1); + + backface_test(shoot); + + drawpatch_ext(shoot, 0x88FF00); + + if(shoot->first->f & RAD_TWOSIDED) { + VECCOPY(unshot, shoot->unshot); + VecNegf(shoot->norm); + if(makeformfactors(shoot)) + applyformfactors(shoot); + VecNegf(shoot->norm); + VECCOPY(shoot->unshot, unshot); + } + + if( makeformfactors(shoot) ) { + applyformfactors(shoot); + + it++; + //XXX set_timecursor(it); + if( (it & 3)==1 ) { + make_node_display(); + rad_forcedraw(); + } + setnodeflags(shoot->first, RAD_SHOOT, 0); + } + + clear_backface_test(); + + //XXX if(blender_test_break()) break; + if(RG.maxiter && RG.maxiter<=it) break; + + shoot=findshootpatch(); + + } + +} + + +/* ************* subdivideshoot *********** */ + +void minmaxradelem(RNode *rn, float *min, float *max) +{ + int c; + + if(rn->down1) { + minmaxradelem(rn->down1, min, max); + minmaxradelem(rn->down2, min, max); + } + else { + for(c=0; c<3; c++) { + min[c]= MIN2(min[c], rn->totrad[c]); + max[c]= MAX2(max[c], rn->totrad[c]); + } + } +} + +void minmaxradelemfilt(RNode *rn, float *min, float *max, float *errmin, float *errmax) +{ + float col[3], area; + int c; + + if(rn->down1) { + minmaxradelemfilt(rn->down1, min, max, errmin, errmax); + minmaxradelemfilt(rn->down2, min, max, errmin, errmax); + } + else { + VECCOPY(col, rn->totrad); + + for(c=0; c<3; c++) { + min[c]= MIN2(min[c], col[c]); + max[c]= MAX2(max[c], col[c]); + } + + VecMulf(col, 2.0); + area= 2.0; + if(rn->ed1) { + VecAddf(col, rn->ed1->totrad, col); + area+= 1.0; + } + if(rn->ed2) { + VecAddf(col, rn->ed2->totrad, col); + area+= 1.0; + } + if(rn->ed3) { + VecAddf(col, rn->ed3->totrad, col); + area+= 1.0; + } + if(rn->ed4) { + VecAddf(col, rn->ed4->totrad, col); + area+= 1.0; + } + VecMulf(col, 1.0/area); + + for(c=0; c<3; c++) { + errmin[c]= MIN2(errmin[c], col[c]); + errmax[c]= MAX2(errmax[c], col[c]); + } + } +} + +static void setsubflagelem(RNode *rn) +{ + + if(rn->down1) { + setsubflagelem(rn->down1); + setsubflagelem(rn->down2); + } + else { + rn->f |= RAD_SUBDIV; + } +} + +static void clearsubflagelem(RNode *rn) +{ + + if(rn->down1) { + setsubflagelem(rn->down1); + setsubflagelem(rn->down2); + } + else { + rn->f &= ~RAD_SUBDIV; + } +} + +void subdivideshootElements(int it) +{ + RPatch *rp, *shoot; + RNode **el, *rn; + float *fp, err, stoke, area, min[3], max[3], errmin[3], errmax[3]; + int a, b, c, d, e, f, contin; + int maxlamp; + + if(RG.maxsublamp==0) maxlamp= RG.totlamp; + else maxlamp= RG.maxsublamp; + + while(it) { + rad_printstatus(); + rad_init_energy(); + it--; + + for(a=0; a<maxlamp; a++) { + shoot= findshootpatch(); + if(shoot==0) break; + + //XXX set_timecursor(a); + drawpatch_ext(shoot, 0x88FF00); + + setnodeflags(shoot->first, RAD_SHOOT, 1); + if( makeformfactors(shoot) ) { + + fp= RG.formfactors; + el= RG.elem; + for(b=RG.totelem; b>0; b--, el++) { + rn= *el; + + if( (rn->f & RAD_SUBDIV)==0 && *fp!=0.0) { + if(rn->par->emit[0]+rn->par->emit[1]+rn->par->emit[2]==0.0) { + + stoke= calcStokefactor(shoot, rn->par, rn, &area); + if(stoke!= 0.0) { + + err= *fp/stoke; + + /* area error */ + area*=(0.5*RG.hemires*RG.hemires); + + if(area>35.0) { + if(err<0.95 || err>1.05) { + if(err>0.05) { + rn->f |= RAD_SUBDIV; + rn->par->f |= RAD_SUBDIV; + } + } + } + } + + } + } + + fp++; + + } + + applyformfactors(shoot); + + if( (a & 3)==1 ) { + make_node_display(); + rad_forcedraw(); + } + + setnodeflags(shoot->first, RAD_SHOOT, 0); + } + else a--; + + //XXX if(blender_test_break()) break; + } + + /* test for extreme small color change within a patch with subdivflag */ + + rp= RG.patchbase.first; + + while(rp) { + if(rp->f & RAD_SUBDIV) { /* rp has elems that need subdiv */ + /* at least 4 levels deep */ + rn= rp->first->down1; + if(rn) { + rn= rn->down1; + if(rn) { + rn= rn->down1; + if(rn) rn= rn->down1; + } + } + if(rn) { + INIT_MINMAX(min, max); + /* errmin and max are the filtered colors */ + INIT_MINMAX(errmin, errmax); + minmaxradelemfilt(rp->first, min, max, errmin, errmax); + + /* if small difference between colors: no subdiv */ + /* also test for the filtered ones: but with higher critical level */ + + contin= 0; + a= abs( calculatecolor(min[0])-calculatecolor(max[0])); + b= abs( calculatecolor(errmin[0])-calculatecolor(errmax[0])); + if(a<15 || b<7) { + c= abs( calculatecolor(min[1])-calculatecolor(max[1])); + d= abs( calculatecolor(errmin[1])-calculatecolor(errmax[1])); + if(c<15 || d<7) { + e= abs( calculatecolor(min[2])-calculatecolor(max[2])); + f= abs( calculatecolor(errmin[2])-calculatecolor(errmax[2])); + if(e<15 || f<7) { + contin= 1; + clearsubflagelem(rp->first); + /* printf("%d %d %d %d %d %d\n", a, b, c, d, e, f); */ + } + } + } + if(contin) { + drawpatch_ext(rp, 0xFFFF); + } + } + } + rp->f &= ~RAD_SUBDIV; + rp= rp->next; + } + + contin= 0; + + el= RG.elem; + for(b=RG.totelem; b>0; b--, el++) { + rn= *el; + if(rn->f & RAD_SUBDIV) { + rn->f-= RAD_SUBDIV; + subdivideNode(rn, 0); + if(rn->down1) { + subdivideNode(rn->down1, 0); + subdivideNode(rn->down2, 0); + contin= 1; + } + } + } + makeGlobalElemArray(); + + //XXX if(contin==0 || blender_test_break()) break; + } + + make_node_display(); +} + +void subdivideshootPatches(int it) +{ + RPatch *rp, *shoot, *next; + float *fp, err, stoke, area; + int a, contin; + int maxlamp; + + if(RG.maxsublamp==0) maxlamp= RG.totlamp; + else maxlamp= RG.maxsublamp; + + while(it) { + rad_printstatus(); + rad_init_energy(); + it--; + + for(a=0; a<maxlamp; a++) { + shoot= findshootpatch(); + if(shoot==0) break; + + //XXX set_timecursor(a); + drawpatch_ext(shoot, 0x88FF00); + + setnodeflags(shoot->first, RAD_SHOOT, 1); + + if( makeformfactors(shoot) ) { + + fp= RG.formfactors; + rp= RG.patchbase.first; + while(rp) { + if(*fp!=0.0 && rp!=shoot) { + + stoke= calcStokefactor(shoot, rp, rp->first, &area); + if(stoke!= 0.0) { + if(area>.1) { /* does patch receive more than (about)10% of energy? */ + rp->f= RAD_SUBDIV; + } + else { + + err= *fp/stoke; + + /* area error */ + area*=(0.5*RG.hemires*RG.hemires); + + if(area>45.0) { + if(err<0.95 || err>1.05) { + if(err>0.05) { + + rp->f= RAD_SUBDIV; + + } + } + } + } + } + } + fp++; + + rp= rp->next; + } + + applyformfactors(shoot); + + if( (a & 3)==1 ) { + make_node_display(); + rad_forcedraw(); + } + + setnodeflags(shoot->first, RAD_SHOOT, 0); + + //XXX if(blender_test_break()) break; + } + else a--; + + } + + contin= 0; + + rp= RG.patchbase.first; + while(rp) { + next= rp->next; + if(rp->f & RAD_SUBDIV) { + if(rp->emit[0]+rp->emit[1]+rp->emit[2]==0.0) { + contin= 1; + subdivideNode(rp->first, 0); + if(rp->first->down1) { + subdivideNode(rp->first->down1, 0); + subdivideNode(rp->first->down2, 0); + } + } + } + rp= next; + } + + converttopatches(); + makeGlobalElemArray(); + + //XXX if(contin==0 || blender_test_break()) break; + } + make_node_display(); +} + +void inithemiwindows() +{ + RadView *vw; + + /* the hemiwindows */ + vw= &(hemitop); + memset(vw, 0, sizeof(RadView)); + vw->rectx= RG.hemires; + vw->recty= RG.hemires; + vw->rectz= MEM_mallocN(sizeof(int)*vw->rectx*vw->recty, "initwindows"); + vw->rect= MEM_mallocN(sizeof(int)*vw->rectx*vw->recty, "initwindows"); + vw->mynear= RG.maxsize/2000.0; + vw->myfar= 2.0*RG.maxsize; + vw->wx1= -vw->mynear; + vw->wx2= vw->mynear; + vw->wy1= -vw->mynear; + vw->wy2= vw->mynear; + + i_window(vw->wx1, vw->wx2, vw->wy1, vw->wy2, vw->mynear, vw->myfar, vw->winmat); + + hemiside= hemitop; + + vw= &(hemiside); + vw->recty/= 2; + vw->wy1= vw->wy2; + vw->wy2= 0.0; + + i_window(vw->wx1, vw->wx2, vw->wy1, vw->wy2, vw->mynear, vw->myfar, vw->winmat); + +} + +void closehemiwindows() +{ + + if(hemiside.rect) MEM_freeN(hemiside.rect); + if(hemiside.rectz) MEM_freeN(hemiside.rectz); + hemiside.rectz= 0; + hemiside.rect= 0; + hemitop.rectz= 0; + hemitop.rect= 0; +} diff --git a/source/blender/radiosity/intern/source/radio.c b/source/blender/radiosity/intern/source/radio.c new file mode 100644 index 00000000000..63032b2d603 --- /dev/null +++ b/source/blender/radiosity/intern/source/radio.c @@ -0,0 +1,390 @@ +/* *************************************** + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + + + + radio.c nov/dec 1992 + may 1999 + + $Id$ + + - mainloop + - interactivity + + + - PREPROCES + - collect meshes + - spitconnected (all faces with different color and normals) + - setedgepointers (nodes pointing to neighbours) + + - EDITING + - min-max patch en min-max element size + - using this info patches subdividing + - lamp subdivide + + - if there are too many lamps for subdivide shooting: + - temporal join patches + + - SUBDIVIDE SHOOTING + - except for last shooting, this defines patch subdivide + - if subdivided patches still > 2*minsize : continue + - at the end create as many elements as possible + - als store if lamp (can still) cause subdivide. + + - REFINEMENT SHOOTING + - test for overflows (shootpatch subdivide) + - testen for extreme color transitions: + - if possible: shootpatch subdivide + - elements subdivide = start over ? + - continue itterate until ? + + - DEFINITIVE SHOOTING + - user indicates how many faces maximum and duration of itteration. + + - POST PROCESS + - join element- nodes when nothing happens in it (filter nodes, filter faces) + - define gamma & mul + + *************************************** */ + +#include <math.h> +#include <string.h> + +#include "MEM_guardedalloc.h" +#include "PIL_time.h" + +#include "BLI_blenlib.h" + +#include "DNA_object_types.h" +#include "DNA_radio_types.h" +#include "DNA_scene_types.h" +#include "DNA_screen_types.h" + +#include "BKE_customdata.h" +#include "BKE_global.h" +#include "BKE_main.h" + +#include "radio.h" + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +/* locals? This one was already done in radio.h... */ +/* void rad_status_str(char *str); */ + +RadGlobal RG= {0, 0}; + +void freeAllRad(Scene *scene) +{ + Base *base; + extern int Ntotvert, Ntotnode, Ntotpatch; + + /* clear flag that disables drawing the meshes */ + if(scene) { + base= (scene->base.first); + while(base) { + if(base->object->type==OB_MESH) { + base->flag &= ~OB_RADIO; + } + base= base->next; + } + } + + free_fastAll(); /* verts, nodes, patches */ + RG.patchbase.first= RG.patchbase.last= 0; + Ntotvert= Ntotnode= Ntotpatch= 0; + + closehemiwindows(); /* not real windows anymore... */ + if(RG.elem) MEM_freeN(RG.elem); + RG.elem= 0; + if(RG.verts) MEM_freeN(RG.verts); + RG.verts= 0; + if(RG.topfactors) MEM_freeN(RG.topfactors); + RG.topfactors= 0; + if(RG.sidefactors) MEM_freeN(RG.sidefactors); + RG.sidefactors= 0; + if(RG.formfactors) MEM_freeN(RG.formfactors); + RG.formfactors= 0; + if(RG.index) MEM_freeN(RG.index); + RG.index= 0; + if(RG.facebase) { + init_face_tab(); /* frees all tables */ + MEM_freeN(RG.facebase); + RG.facebase= 0; + } + + if(RG.mfdata) { + CustomData_free(RG.mfdata, RG.mfdatatot); + MEM_freeN(RG.mfdata); + MEM_freeN(RG.mfdatanodes); + RG.mfdatanodes= NULL; + RG.mfdata= NULL; + RG.mfdatatot= 0; + } + RG.totelem= RG.totpatch= RG.totvert= RG.totface= RG.totlamp= RG.totmat= 0; +} + +int rad_phase() +{ + int flag= 0; + + if(RG.totpatch) flag |= RAD_PHASE_PATCHES; + if(RG.totface) flag |= RAD_PHASE_FACES; + + return flag; +} + +void rad_status_str(char *str) +{ + extern int totfastmem; + int tot; + char *phase; + + tot= (RG.totface*sizeof(Face))/1024; + tot+= totfastmem/1024; + + if(RG.phase==RAD_SHOOTE) phase= "Phase: ELEMENT SUBD, "; + else if(RG.phase==RAD_SHOOTP) phase= "Phase: PATCH SUBD, "; + else if(RG.phase==RAD_SOLVE) phase= "Phase: SOLVE, "; + else if(RG.totpatch==0) phase= "Phase: COLLECT MESHES "; + else if(RG.totface) phase= "Phase: FINISHED, "; + else phase= "Phase: INIT, "; + + if(RG.totpatch==0) strcpy(str, phase); + else sprintf(str, "%s TotPatch: %d TotElem: %d Emit: %d Faces %d Mem: %d k ", phase, RG.totpatch, RG.totelem, RG.totlamp, RG.totface, tot); + + if(RG.phase==RAD_SOLVE) strcat(str, "(press ESC to stop)"); +} + +void rad_printstatus() +{ + /* actions always are started from a buttonswindow */ +// XX if(curarea) { +// scrarea_do_windraw(curarea); +// screen_swapbuffers(); +// } +} + +void rad_setlimits(Scene *scene) +{ + Radio *rad= scene->radio; + float fac; + + fac= 0.0005*rad->pama; + RG.patchmax= RG.maxsize*fac; + RG.patchmax*= RG.patchmax; + fac= 0.0005*rad->pami; + RG.patchmin= RG.maxsize*fac; + RG.patchmin*= RG.patchmin; + + fac= 0.0005*rad->elma; + RG.elemmax= RG.maxsize*fac; + RG.elemmax*= RG.elemmax; + fac= 0.0005*rad->elmi; + RG.elemmin= RG.maxsize*fac; + RG.elemmin*= RG.elemmin; +} + +void set_radglobal(Scene *scene) +{ + /* always call before any action is performed */ + Radio *rad= scene->radio; + + if(RG.radio==0) { + /* firsttime and to be sure */ + memset(&RG, 0, sizeof(RadGlobal)); + } + + if(rad==0) return; + + if(rad != RG.radio) { + if(RG.radio) freeAllRad(scene); + memset(&RG, 0, sizeof(RadGlobal)); + RG.radio= rad; + } + + RG.hemires= rad->hemires & 0xFFF0; + RG.drawtype= rad->drawtype; + RG.flag= rad->flag; + RG.subshootp= rad->subshootp; + RG.subshoote= rad->subshoote; + RG.nodelim= rad->nodelim; + RG.maxsublamp= rad->maxsublamp; + RG.maxnode= 2*rad->maxnode; /* in button:max elem, subdividing! */ + RG.convergence= rad->convergence/1000.0; + RG.radfac= rad->radfac; + RG.gamma= rad->gamma; + RG.maxiter= rad->maxiter; + + RG.re= NULL; /* struct render, for when call it from render engine */ + + rad_setlimits(scene); +} + +/* called from buttons.c */ +void add_radio(Scene *scene) +{ + Radio *rad; + + if(scene->radio) MEM_freeN(scene->radio); + rad= scene->radio= MEM_callocN(sizeof(Radio), "radio"); + + rad->hemires= 300; + rad->convergence= 0.1; + rad->radfac= 30.0; + rad->gamma= 2.0; + rad->drawtype= RAD_SOLID; + rad->subshootp= 1; + rad->subshoote= 2; + rad->maxsublamp= 0; + + rad->pama= 500; + rad->pami= 200; + rad->elma= 100; + rad->elmi= 20; + rad->nodelim= 0; + rad->maxnode= 10000; + rad->maxiter= 120; // arbitrary + rad->flag= 2; + set_radglobal(scene); +} + +void delete_radio(Scene *scene) +{ + freeAllRad(scene); + if(scene->radio) MEM_freeN(scene->radio); + scene->radio= 0; + + RG.radio= 0; +} + +int rad_go(Scene *scene) /* return 0 when user escapes */ +{ + double stime= PIL_check_seconds_timer(); + int retval; + + if(RG.totface) return 0; + + G.afbreek= 0; + + set_radglobal(scene); + initradiosity(); /* LUT's */ + inithemiwindows(); /* views */ + + maxsizePatches(); + + setnodelimit(RG.patchmin); + RG.phase= RAD_SHOOTP; + subdivideshootPatches(RG.subshootp); + + setnodelimit(RG.elemmin); + RG.phase= RAD_SHOOTE; + subdivideshootElements(RG.subshoote); + + setnodelimit(RG.patchmin); + subdividelamps(); + + setnodelimit(RG.elemmin); + + RG.phase= RAD_SOLVE; + subdiv_elements(); + + progressiverad(); + + removeEqualNodes(RG.nodelim); + + make_face_tab(); /* now anchored */ + + closehemiwindows(); + RG.phase= 0; + + stime= PIL_check_seconds_timer()-stime; + printf("Radiosity solving time: %dms\n", (int) (stime*1000)); + + if(G.afbreek==1) retval= 1; + else retval= 0; + + G.afbreek= 0; + + return retval; +} + +void rad_subdivshootpatch(Scene *scene) +{ + + if(RG.totface) return; + + G.afbreek= 0; + + set_radglobal(scene); + initradiosity(); /* LUT's */ + inithemiwindows(); /* views */ + + subdivideshootPatches(1); + + removeEqualNodes(RG.nodelim); + closehemiwindows(); + +// XXX allqueue(REDRAWVIEW3D, 1); +} + +void rad_subdivshootelem(Scene *scene) +{ + + if(RG.totface) return; + + G.afbreek= 0; + + set_radglobal(scene); + initradiosity(); /* LUT's */ + inithemiwindows(); /* views */ + + subdivideshootElements(1); + + removeEqualNodes(RG.nodelim); + closehemiwindows(); + +// XXX allqueue(REDRAWVIEW3D, 1); +} + +void rad_limit_subdivide(Scene *scene) +{ + + if(scene->radio==0) return; + + set_radglobal(scene); + + if(RG.totpatch==0) { + /* printf("exit: no relevant data\n"); */ + return; + } + + maxsizePatches(); + + init_face_tab(); /* free faces */ +} diff --git a/source/blender/radiosity/intern/source/radnode.c b/source/blender/radiosity/intern/source/radnode.c new file mode 100644 index 00000000000..fa23ca5da57 --- /dev/null +++ b/source/blender/radiosity/intern/source/radnode.c @@ -0,0 +1,1103 @@ +/* *************************************** + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + + + + node.c nov/dec 1992 + may 1999 + + $Id$ + + *************************************** */ + +#include <stdio.h> +#include <math.h> +#include <string.h> + +#include "MEM_guardedalloc.h" + +#include "BLI_blenlib.h" +#include "BLI_arithb.h" + +#include "BKE_global.h" +#include "BKE_main.h" + +#include "radio.h" + +#include "BLO_sys_types.h" // for intptr_t support + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +/* locals */ +static void *malloc_fast(int size); +static void *calloc_fast(int size); +static void free_fast(void *poin, int siz); +static void deleteTriNodes(RNode *node); +/* lower because of local type define */ +/* void check_mallocgroup(MallocGroup *mg); */ + + +/* ********** fastmalloc ************** */ + +#define MAL_GROUPSIZE 256 +#define MAL_AVAILABLE 1 +#define MAL_FULL 2 + + + + +ListBase MallocBase= {0, 0}; +int totfastmem= 0; + +typedef struct MallocGroup { + struct MallocGroup *next, *prev; + short size, flag; + short curfree, tot; + char flags[MAL_GROUPSIZE]; + char *data; +} MallocGroup; + +/* one more local */ +void check_mallocgroup(MallocGroup *mg); + +void check_mallocgroup(MallocGroup *mg) +{ + int a; + char *cp; + + if(mg->tot==MAL_GROUPSIZE) { + mg->flag= MAL_FULL; + return; + } + + cp= mg->flags; + + if(mg->curfree<MAL_GROUPSIZE-1) { + if(cp[mg->curfree+1]==0) { + mg->curfree++; + return; + } + } + if(mg->curfree>0) { + if(cp[mg->curfree-1]==0) { + mg->curfree--; + return; + } + } + + for(a=0; a<MAL_GROUPSIZE; a++) { + if(cp[a]==0) { + mg->curfree= a; + return; + } + } + printf("fastmalloc: shouldnt be here\n"); +} + +static void *malloc_fast(int size) +{ + MallocGroup *mg; + void *retval; + + mg= MallocBase.last; + while(mg) { + if(mg->size==size) { + if(mg->flag & MAL_AVAILABLE) { + mg->flags[mg->curfree]= 1; + mg->tot++; + retval= mg->data+mg->curfree*mg->size; + check_mallocgroup(mg); + return retval; + } + } + mg= mg->prev; + } + + /* no free block found */ + mg= MEM_callocN(sizeof(MallocGroup), "mallocgroup"); + BLI_addtail(&MallocBase, mg); + mg->data= MEM_mallocN(MAL_GROUPSIZE*size, "mallocgroupdata"); + mg->flag= MAL_AVAILABLE; + mg->flags[0]= 1; + mg->curfree= 1; + mg->size= size; + mg->tot= 1; + + totfastmem+= sizeof(MallocGroup)+MAL_GROUPSIZE*size; + + return mg->data; +} + +static void *calloc_fast(int size) +{ + void *poin; + + poin= malloc_fast(size); + memset(poin, 0, size); + + return poin; +} + +static void free_fast(void *poin, int size) +{ + MallocGroup *mg; + intptr_t val; + + mg= MallocBase.last; + while(mg) { + if(mg->size==size) { + if( ((intptr_t)poin) >= ((intptr_t)mg->data) ) { + if( ((intptr_t)poin) < ((intptr_t)(mg->data+MAL_GROUPSIZE*size)) ) { + val= ((intptr_t)poin) - ((intptr_t)mg->data); + val/= size; + mg->curfree= val; + mg->flags[val]= 0; + mg->flag= MAL_AVAILABLE; + + mg->tot--; + if(mg->tot==0) { + BLI_remlink(&MallocBase, mg); + MEM_freeN(mg->data); + MEM_freeN(mg); + totfastmem-= sizeof(MallocGroup)+MAL_GROUPSIZE*size; + } + return; + } + } + } + mg= mg->prev; + } + printf("fast free: pointer not in memlist %p size %d\n", + poin, size); +} + +/* security: only one function in a time can use it */ +static char *fastmallocstr= 0; + +void free_fastAll() +{ + MallocGroup *mg; + + mg= MallocBase.first; + while(mg) { + BLI_remlink(&MallocBase, mg); + MEM_freeN(mg->data); + MEM_freeN(mg); + mg= MallocBase.first; + } + totfastmem= 0; + fastmallocstr= 0; +} + +void start_fastmalloc(char *str) +{ + if(fastmallocstr) { +// XXX error("Fastmalloc in use: %s", fastmallocstr); + return; + } + fastmallocstr= str; +} + +/* **************************************** */ + +float nodelimit; + +void setnodelimit(float limit) +{ + nodelimit= limit; + +} + +/* ************ memory management *********** */ + +int Ntotvert=0, Ntotnode=0, Ntotpatch=0; + +float *mallocVert() +{ + Ntotvert++; + return (float *)malloc_fast(16); +} + +float *callocVert() +{ + Ntotvert++; + return (float *)calloc_fast(16); +} + +void freeVert(float *vert) +{ + free_fast(vert, 16); + Ntotvert--; +} + +int totalRadVert() +{ + return Ntotvert; +} + +RNode *mallocNode() +{ + Ntotnode++; + return (RNode *)malloc_fast(sizeof(RNode)); +} + +RNode *callocNode() +{ + Ntotnode++; + return (RNode *)calloc_fast(sizeof(RNode)); +} + +void freeNode(RNode *node) +{ + free_fast(node, sizeof(RNode)); + Ntotnode--; +} + +void freeNode_recurs(RNode *node) +{ + + if(node->down1) { + freeNode_recurs(node->down1); + freeNode_recurs(node->down2); + } + + node->down1= node->down2= 0; + freeNode(node); + +} + +RPatch *mallocPatch() +{ + Ntotpatch++; + return (RPatch *)malloc_fast(sizeof(RPatch)); +} + +RPatch *callocPatch() +{ + Ntotpatch++; + return (RPatch *)calloc_fast(sizeof(RPatch)); +} + +void freePatch(RPatch *patch) +{ + free_fast(patch, sizeof(RPatch)); + Ntotpatch--; +} + +/* ************ SUBDIVIDE *********** */ + + +void replaceAllNode(RNode *neighb, RNode *newn) +{ + /* changes from all neighbours the edgepointers that point to newn->up in new */ + int ok= 0; + + + if(neighb==0) return; + if(newn->up==0) return; + + if(neighb->ed1==newn->up) { + neighb->ed1= newn; + ok= 1; + } + else if(neighb->ed2==newn->up) { + neighb->ed2= newn; + ok= 1; + } + else if(neighb->ed3==newn->up) { + neighb->ed3= newn; + ok= 1; + } + else if(neighb->ed4==newn->up) { + neighb->ed4= newn; + ok= 1; + } + + if(ok && neighb->down1) { + replaceAllNode(neighb->down1, newn); + replaceAllNode(neighb->down2, newn); + } +} + +void replaceAllNodeInv(RNode *neighb, RNode *old) +{ + /* changes from all neighbours the edgepointers that point to old in old->up */ + if(neighb==0) return; + if(old->up==0) return; + + if(neighb->ed1==old) { + neighb->ed1= old->up; + } + else if(neighb->ed2==old) { + neighb->ed2= old->up; + } + else if(neighb->ed3==old) { + neighb->ed3= old->up; + } + else if(neighb->ed4==old) { + neighb->ed4= old->up; + } + + if(neighb->down1) { + replaceAllNodeInv(neighb->down1, old); + replaceAllNodeInv(neighb->down2, old); + } +} + +void replaceAllNodeUp(RNode *neighb, RNode *old) +{ + /* changes from all neighbours the edgepointers that point to old in old->up */ + if(neighb==0) return; + if(old->up==0) return; + neighb= neighb->up; + if(neighb==0) return; + + if(neighb->ed1==old) { + neighb->ed1= old->up; + } + else if(neighb->ed2==old) { + neighb->ed2= old->up; + } + else if(neighb->ed3==old) { + neighb->ed3= old->up; + } + else if(neighb->ed4==old) { + neighb->ed4= old->up; + } + + if(neighb->up) { + replaceAllNodeUp(neighb, old); + } +} + + +void replaceTestNode(RNode *neighb, RNode **edpp, RNode *newn, int level, float *vert) +{ + /* IF neighb->ed points to newn->up + * IF edgelevels equal + IF testvert is in neighb->ed + change pointers both ways + ELSE + RETURN + ELSE + IF neighb edgelevel is deeper + change neighb pointer + + */ + int ok= 0; + + if(neighb==0) return; + if(newn->up==0) return; + + if(neighb->ed1==newn->up) { + if(neighb->lev1==level) { + if(vert==neighb->v1 || vert==neighb->v2) { + *edpp= neighb; + neighb->ed1= newn; + } + else return; + } + else if(neighb->lev1>level) { + neighb->ed1= newn; + } + ok= 1; + } + else if(neighb->ed2==newn->up) { + if(neighb->lev2==level) { + if(vert==neighb->v2 || vert==neighb->v3) { + *edpp= neighb; + neighb->ed2= newn; + } + else return; + } + else if(neighb->lev2>level) { + neighb->ed2= newn; + } + ok= 1; + } + else if(neighb->ed3==newn->up) { + if(neighb->lev3==level) { + if(neighb->type==3) { + if(vert==neighb->v3 || vert==neighb->v1) { + *edpp= neighb; + neighb->ed3= newn; + } + else return; + } + else { + if(vert==neighb->v3 || vert==neighb->v4) { + *edpp= neighb; + neighb->ed3= newn; + } + else return; + } + } + else if(neighb->lev3>level) { + neighb->ed3= newn; + } + ok= 1; + } + else if(neighb->ed4==newn->up) { + if(neighb->lev4==level) { + if(vert==neighb->v4 || vert==neighb->v1) { + *edpp= neighb; + neighb->ed4= newn; + } + else return; + } + else if(neighb->lev4>level) { + neighb->ed4= newn; + } + ok= 1; + } + + if(ok && neighb->down1) { + replaceTestNode(neighb->down1, edpp, newn, level, vert); + replaceTestNode(neighb->down2, edpp, newn, level, vert); + } + +} + +int setvertexpointersNode(RNode *neighb, RNode *node, int level, float **v1, float **v2) +{ + /* compares edgelevels , if equal it sets the vertexpointers */ + + if(neighb==0) return 0; + + if(neighb->ed1==node) { + if(neighb->lev1==level) { + *v1= neighb->v1; + *v2= neighb->v2; + return 1; + } + } + else if(neighb->ed2==node) { + if(neighb->lev2==level) { + *v1= neighb->v2; + *v2= neighb->v3; + return 1; + } + } + else if(neighb->ed3==node) { + if(neighb->lev3==level) { + if(neighb->type==3) { + *v1= neighb->v3; + *v2= neighb->v1; + } + else { + *v1= neighb->v3; + *v2= neighb->v4; + } + return 1; + } + } + else if(neighb->ed4==node) { + if(neighb->lev4==level) { + *v1= neighb->v4; + *v2= neighb->v1; + return 1; + } + } + return 0; +} + +float edlen(float *v1, float *v2) +{ + return (v1[0]-v2[0])*(v1[0]-v2[0])+ (v1[1]-v2[1])*(v1[1]-v2[1])+ (v1[2]-v2[2])*(v1[2]-v2[2]); +} + + +void subdivideTriNode(RNode *node, RNode *edge) +{ + RNode *n1, *n2, *up; + float fu, fv, fl, *v1, *v2; /* , AreaT3Dfl(); ... from arithb... */ + int uvl; + + if(node->down1 || node->down2) { + /* printf("trinode: subd already done\n"); */ + return; + } + + /* defines subdivide direction */ + + if(edge==0) { + /* areathreshold */ + if(node->area<nodelimit) return; + + fu= edlen(node->v1, node->v2); + fv= edlen(node->v2, node->v3); + fl= edlen(node->v3, node->v1); + + if(fu>fv && fu>fl) uvl= 1; + else if(fv>fu && fv>fl) uvl= 2; + else uvl= 3; + } + else { + + if(edge==node->ed1) uvl= 1; + else if(edge==node->ed2) uvl= 2; + else uvl= 3; + } + + /* should neighbour nodes be deeper? Recursive! */ + n1= 0; + if(uvl==1) { + if(node->ed1 && node->ed1->down1==0) n1= node->ed1; + } + else if(uvl==2) { + if(node->ed2 && node->ed2->down1==0) n1= node->ed2; + } + else { + if(node->ed3 && node->ed3->down1==0) n1= node->ed3; + } + if(n1) { + up= node->up; + while(up) { /* also test for ed4 !!! */ + if(n1->ed1==up || n1->ed2==up || n1->ed3==up || n1->ed4==up) { + subdivideNode(n1, up); + break; + } + up= up->up; + } + } + + /* the subdividing */ + n1= mallocNode(); + memcpy(n1, node, sizeof(RNode)); + n2= mallocNode(); + memcpy(n2, node, sizeof(RNode)); + + n1->up= node; + n2->up= node; + + node->down1= n1; + node->down2= n2; + + /* subdivide edge 1 */ + if(uvl==1) { + + /* FIRST NODE gets edge 2 */ + n1->ed3= n2; + n1->lev3= 0; + replaceAllNode(n1->ed2, n1); + n1->lev1++; + replaceTestNode(n1->ed1, &(n1->ed1), n1, n1->lev1, n1->v2); + + /* SECOND NODE gets edge 3 */ + n2->ed2= n1; + n2->lev2= 0; + replaceAllNode(n2->ed3, n2); + n2->lev1++; + replaceTestNode(n2->ed1, &(n2->ed1), n2, n2->lev1, n2->v1); + + /* NEW VERTEX from edge 1 */ + if( setvertexpointersNode(n1->ed1, n1, n1->lev1, &v1, &v2) ) { /* nodes have equal levels */ + if(v1== n1->v2) { + n1->v1= v2; + n2->v2= v2; + } + else { + n1->v1= v1; + n2->v2= v1; + } + } + else { + n1->v1= n2->v2= mallocVert(); + n1->v1[0]= 0.5*(node->v1[0]+ node->v2[0]); + n1->v1[1]= 0.5*(node->v1[1]+ node->v2[1]); + n1->v1[2]= 0.5*(node->v1[2]+ node->v2[2]); + n1->v1[3]= node->v1[3]; /* color */ + } + } + else if(uvl==2) { + + /* FIRST NODE gets edge 1 */ + n1->ed3= n2; + n1->lev3= 0; + replaceAllNode(n1->ed1, n1); + n1->lev2++; + replaceTestNode(n1->ed2, &(n1->ed2), n1, n1->lev2, n1->v2); + + /* SECOND NODE gets edge 3 */ + n2->ed1= n1; + n2->lev1= 0; + replaceAllNode(n2->ed3, n2); + n2->lev2++; + replaceTestNode(n2->ed2, &(n2->ed2), n2, n2->lev2, n2->v3); + + /* NEW VERTEX from edge 2 */ + if( setvertexpointersNode(n1->ed2, n1, n1->lev2, &v1, &v2) ) { /* nodes have equal levels */ + if(v1== n1->v2) { + n1->v3= v2; + n2->v2= v2; + } + else { + n1->v3= v1; + n2->v2= v1; + } + } + else { + n1->v3= n2->v2= mallocVert(); + n1->v3[0]= 0.5*(node->v2[0]+ node->v3[0]); + n1->v3[1]= 0.5*(node->v2[1]+ node->v3[1]); + n1->v3[2]= 0.5*(node->v2[2]+ node->v3[2]); + n1->v3[3]= node->v1[3]; /* color */ + } + } + else if(uvl==3) { + + /* FIRST NODE gets edge 1 */ + n1->ed2= n2; + n1->lev2= 0; + replaceAllNode(n1->ed1, n1); + n1->lev3++; + replaceTestNode(n1->ed3, &(n1->ed3), n1, n1->lev3, n1->v1); + + /* SECOND NODE gets edge 2 */ + n2->ed1= n1; + n2->lev1= 0; + replaceAllNode(n2->ed2, n2); + n2->lev3++; + replaceTestNode(n2->ed3, &(n2->ed3), n2, n2->lev3, n2->v3); + + /* NEW VERTEX from edge 3 */ + if( setvertexpointersNode(n1->ed3, n1, n1->lev3, &v1, &v2) ) { /* nodes have equal levels */ + if(v1== n1->v1) { + n1->v3= v2; + n2->v1= v2; + } + else { + n1->v3= v1; + n2->v1= v1; + } + } + else { + n1->v3= n2->v1= mallocVert(); + n1->v3[0]= 0.5*(node->v1[0]+ node->v3[0]); + n1->v3[1]= 0.5*(node->v1[1]+ node->v3[1]); + n1->v3[2]= 0.5*(node->v1[2]+ node->v3[2]); + n1->v3[3]= node->v3[3]; /* color */ + } + } + n1->area= AreaT3Dfl(n1->v1, n1->v2, n1->v3); + n2->area= AreaT3Dfl(n2->v1, n2->v2, n2->v3); + +} + + +void subdivideNode(RNode *node, RNode *edge) +{ + RNode *n1, *n2, *up; + float fu, fv, *v1, *v2;/*, AreaQ3Dfl(); ... from arithb... */ + int uvl; + + if(Ntotnode>RG.maxnode) return; + + if(node->type==3) { + subdivideTriNode(node, edge); + return; + } + + if(node->down1 || node->down2) { + /* printf("subdivide Node: already done \n"); */ + return; + } + + /* defines subdivide direction */ + + if(edge==0) { + /* areathreshold */ + if(node->area<nodelimit) { + return; + } + fu= fabs(node->v1[0]- node->v2[0])+ fabs(node->v1[1]- node->v2[1]) +fabs(node->v1[2]- node->v2[2]); + fv= fabs(node->v1[0]- node->v4[0])+ fabs(node->v1[1]- node->v4[1]) +fabs(node->v1[2]- node->v4[2]); + if(fu>fv) uvl= 1; + else uvl= 2; + } + else { + if(edge==node->ed1 || edge==node->ed3) uvl= 1; + else uvl= 2; + } + + /* do neighbour nodes have to be deeper? Recursive! */ + n1= n2= 0; + if(uvl==1) { + if(node->ed1 && node->ed1->down1==0) n1= node->ed1; + if(node->ed3 && node->ed3->down1==0) n2= node->ed3; + } + else { + if(node->ed2 && node->ed2->down1==0) n1= node->ed2; + if(node->ed4 && node->ed4->down1==0) n2= node->ed4; + } + if(n1) { + up= node->up; + while(up) { + if(n1->ed1==up || n1->ed2==up || n1->ed3==up || n1->ed4==up) { + /* printf("recurs subd\n"); */ + subdivideNode(n1, up); + break; + } + up= up->up; + } + } + if(n2) { + up= node->up; + while(up) { + if(n2->ed1==up || n2->ed2==up || n2->ed3==up || n2->ed4==up) { + /* printf("recurs subd\n"); */ + subdivideNode(n2, up); + break; + } + up= up->up; + } + } + + /* the subdividing */ + n1= mallocNode(); + memcpy(n1, node, sizeof(RNode)); + n2= mallocNode(); + memcpy(n2, node, sizeof(RNode)); + + n1->up= node; + n2->up= node; + + node->down1= n1; + node->down2= n2; + + /* subdivide edge 1 and 3 */ + if(uvl==1) { + + /* FIRST NODE gets edge 2 */ + n1->ed4= n2; + n1->lev4= 0; + replaceAllNode(n1->ed2, n1); + n1->lev1++; + n1->lev3++; + replaceTestNode(n1->ed1, &(n1->ed1), n1, n1->lev1, n1->v2); + replaceTestNode(n1->ed3, &(n1->ed3), n1, n1->lev3, n1->v3); + + /* SECOND NODE gets edge 4 */ + n2->ed2= n1; + n2->lev2= 0; + replaceAllNode(n2->ed4, n2); + n2->lev1++; + n2->lev3++; + replaceTestNode(n2->ed1, &(n2->ed1), n2, n2->lev1, n2->v1); + replaceTestNode(n2->ed3, &(n2->ed3), n2, n2->lev3, n2->v4); + + /* NEW VERTEX from edge 1 */ + if( setvertexpointersNode(n1->ed1, n1, n1->lev1, &v1, &v2) ) { /* nodes have equal levels */ + if(v1== n1->v2) { + n1->v1= v2; + n2->v2= v2; + } + else { + n1->v1= v1; + n2->v2= v1; + } + } + else { + n1->v1= n2->v2= mallocVert(); + n1->v1[0]= 0.5*(node->v1[0]+ node->v2[0]); + n1->v1[1]= 0.5*(node->v1[1]+ node->v2[1]); + n1->v1[2]= 0.5*(node->v1[2]+ node->v2[2]); + n1->v1[3]= node->v1[3]; /* color */ + } + + /* NEW VERTEX from edge 3 */ + if( setvertexpointersNode(n1->ed3, n1, n1->lev3, &v1, &v2) ) { /* nodes have equal levels */ + if(v1== n1->v3) { + n1->v4= v2; + n2->v3= v2; + } + else { + n1->v4= v1; + n2->v3= v1; + } + } + else { + n1->v4= n2->v3= mallocVert(); + n1->v4[0]= 0.5*(node->v3[0]+ node->v4[0]); + n1->v4[1]= 0.5*(node->v3[1]+ node->v4[1]); + n1->v4[2]= 0.5*(node->v3[2]+ node->v4[2]); + n1->v4[3]= node->v4[3]; /* color */ + } + } + /* subdivide edge 2 and 4 */ + else if(uvl==2) { + + /* FIRST NODE gets edge 1 */ + n1->ed3= n2; + n1->lev3= 0; + replaceAllNode(n1->ed1, n1); + n1->lev2++; + n1->lev4++; + replaceTestNode(n1->ed2, &(n1->ed2), n1, n1->lev2, n1->v2); + replaceTestNode(n1->ed4, &(n1->ed4), n1, n1->lev4, n1->v1); + + /* SECOND NODE gets edge 3 */ + n2->ed1= n1; + n2->lev1= 0; + replaceAllNode(n2->ed3, n2); + n2->lev2++; + n2->lev4++; + replaceTestNode(n2->ed2, &(n2->ed2), n2, n2->lev2, n2->v3); + replaceTestNode(n2->ed4, &(n2->ed4), n2, n2->lev4, n2->v4); + + /* NEW VERTEX from edge 2 */ + if( setvertexpointersNode(n1->ed2, n1, n1->lev2, &v1, &v2) ) { /* nodes have equal levels */ + if(v1== n1->v2) { + n1->v3= v2; + n2->v2= v2; + } + else { + n1->v3= v1; + n2->v2= v1; + } + } + else { + n1->v3= n2->v2= mallocVert(); + n1->v3[0]= 0.5*(node->v2[0]+ node->v3[0]); + n1->v3[1]= 0.5*(node->v2[1]+ node->v3[1]); + n1->v3[2]= 0.5*(node->v2[2]+ node->v3[2]); + n1->v3[3]= node->v3[3]; /* color */ + } + + /* NEW VERTEX from edge 4 */ + if( setvertexpointersNode(n1->ed4, n1, n1->lev4, &v1, &v2) ) { /* nodes have equal levels */ + if(v1== n1->v1) { + n1->v4= v2; + n2->v1= v2; + } + else { + n1->v4= v1; + n2->v1= v1; + } + } + else { + n1->v4= n2->v1= mallocVert(); + n1->v4[0]= 0.5*(node->v1[0]+ node->v4[0]); + n1->v4[1]= 0.5*(node->v1[1]+ node->v4[1]); + n1->v4[2]= 0.5*(node->v1[2]+ node->v4[2]); + n1->v4[3]= node->v4[3]; /* color */ + } + } + + n1->area= AreaQ3Dfl(n1->v1, n1->v2, n1->v3, n1->v4); + n2->area= AreaQ3Dfl(n2->v1, n2->v2, n2->v3, n2->v4); + +} + +int comparelevel(RNode *node, RNode *nb, int level) +{ + /* recursive descent: test with deepest node */ + /* return 1 means equal or higher */ + + if(nb==0) return 1; + + if(nb->down1) { + return 0; + + /* THERE IS AN ERROR HERE, BUT WHAT? (without this function the system + works too, but is slower) (ton) */ + + /* + n1= nb->down1; + if(n1->ed1==node) return comparelevel(node, n1, level); + if(n1->ed2==node) return comparelevel(node, n1, level); + if(n1->ed3==node) return comparelevel(node, n1, level); + if(n1->ed4==node) return comparelevel(node, n1, level); + n1= nb->down2; + if(n1->ed1==node) return comparelevel(node, n1, level); + if(n1->ed2==node) return comparelevel(node, n1, level); + if(n1->ed3==node) return comparelevel(node, n1, level); + if(n1->ed4==node) return comparelevel(node, n1, level); + printf(" dit kan niet "); + return 0; + */ + + } + + if(nb->down1==0) { + /* if(nb->ed1==node) return (nb->lev1<=level); */ + /* if(nb->ed2==node) return (nb->lev2<=level); */ + /* if(nb->ed3==node) return (nb->lev3<=level); */ + /* if(nb->ed4==node) return (nb->lev4<=level); */ + + return 1; /* is higher node */ + } + return 1; +} + +static void deleteTriNodes(RNode *node) /* both children of node */ +{ + RNode *n1, *n2; + + /* if neighbour nodes are deeper: no delete */ + /* just test 2 nodes, from the others the level doesn't change */ + + n1= node->down1; + n2= node->down2; + + if(n1==0 || n2==0) return; + + if(n1->down1 || n2->down1) return; + + /* at the edges no subdivided node is allowed */ + + if(n1->ed1 && n1->ed1->down1) return; + if(n1->ed2 && n1->ed2->down1) return; + if(n1->ed3 && n1->ed3->down1) return; + + if(n2->ed1 && n2->ed1->down1) return; + if(n2->ed2 && n2->ed2->down1) return; + if(n2->ed3 && n2->ed3->down1) return; + + replaceAllNodeInv(n1->ed1, n1); + replaceAllNodeInv(n1->ed2, n1); + replaceAllNodeInv(n1->ed3, n1); + + replaceAllNodeUp(n1->ed1, n1); + replaceAllNodeUp(n1->ed2, n1); + replaceAllNodeUp(n1->ed3, n1); + + replaceAllNodeInv(n2->ed1, n2); + replaceAllNodeInv(n2->ed2, n2); + replaceAllNodeInv(n2->ed3, n2); + + replaceAllNodeUp(n2->ed1, n2); + replaceAllNodeUp(n2->ed2, n2); + replaceAllNodeUp(n2->ed3, n2); + + n1->down1= (RNode *)12; /* for debug */ + n2->down1= (RNode *)12; + + freeNode(n1); + freeNode(n2); + node->down1= node->down2= 0; + +} + + /* both children of node */ +void deleteNodes(RNode *node) +{ + RNode *n1, *n2; + + /* if neighbour nodes are deeper: no delete */ + /* just test 2 nodes, from the others the level doesn't change */ + + if(node->type==3) { + deleteTriNodes(node); + return; + } + + n1= node->down1; + n2= node->down2; + + if(n1==0 || n2==0) return; + + if(n1->down1 || n2->down1) return; + + if(n1->ed3==n2) { + + /* at the edges no subdivided node is allowed */ + + if(n1->ed1 && n1->ed1->down1) return; + if(n1->ed2 && n1->ed2->down1) return; + if(n1->ed4 && n1->ed4->down1) return; + + if(n2->ed2 && n2->ed2->down1) return; + if(n2->ed3 && n2->ed3->down1) return; + if(n2->ed4 && n2->ed4->down1) return; + + replaceAllNodeInv(n1->ed1, n1); + replaceAllNodeInv(n1->ed2, n1); + replaceAllNodeInv(n1->ed4, n1); + + replaceAllNodeUp(n1->ed1, n1); + replaceAllNodeUp(n1->ed2, n1); + replaceAllNodeUp(n1->ed4, n1); + + replaceAllNodeInv(n2->ed2, n2); + replaceAllNodeInv(n2->ed3, n2); + replaceAllNodeInv(n2->ed4, n2); + + replaceAllNodeUp(n2->ed2, n2); + replaceAllNodeUp(n2->ed3, n2); + replaceAllNodeUp(n2->ed4, n2); + + n1->down1= (RNode *)12; /* for debug */ + n2->down1= (RNode *)12; + + freeNode(n1); + freeNode(n2); + node->down1= node->down2= 0; + + return; + } + else if(n1->ed4==n2) { + + if(n1->ed1 && n1->ed1->down1) return; + if(n1->ed2 && n1->ed2->down1) return; + if(n1->ed3 && n1->ed3->down1) return; + + if(n2->ed1 && n2->ed1->down1) return; + if(n2->ed3 && n2->ed3->down1) return; + if(n2->ed4 && n2->ed4->down1) return; + + replaceAllNodeInv(n1->ed1, n1); + replaceAllNodeInv(n1->ed2, n1); + replaceAllNodeInv(n1->ed3, n1); + + replaceAllNodeUp(n1->ed1, n1); + replaceAllNodeUp(n1->ed2, n1); + replaceAllNodeUp(n1->ed3, n1); + + replaceAllNodeInv(n2->ed1, n2); + replaceAllNodeInv(n2->ed3, n2); + replaceAllNodeInv(n2->ed4, n2); + + replaceAllNodeUp(n2->ed1, n2); + replaceAllNodeUp(n2->ed3, n2); + replaceAllNodeUp(n2->ed4, n2); + + n1->down1= (RNode *)12; /* for debug */ + n2->down1= (RNode *)12; + + freeNode(n1); + freeNode(n2); + node->down1= node->down2= 0; + + return; + } + +} + + diff --git a/source/blender/radiosity/intern/source/radpostprocess.c b/source/blender/radiosity/intern/source/radpostprocess.c new file mode 100644 index 00000000000..6912c737a51 --- /dev/null +++ b/source/blender/radiosity/intern/source/radpostprocess.c @@ -0,0 +1,824 @@ +/* *************************************** + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + + + + radpostprocess.c nov/dec 1992 + may 1999 + + - faces + - filtering and node-limit + - apply to meshes + $Id$ + + *************************************** */ + +#include <stdlib.h> +#include <string.h> +#include <math.h> + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +#include "MEM_guardedalloc.h" + +#include "BLI_blenlib.h" +#include "BLI_arithb.h" +#include "BLI_ghash.h" + +#include "DNA_material_types.h" +#include "DNA_mesh_types.h" +#include "DNA_meshdata_types.h" +#include "DNA_object_types.h" +#include "DNA_radio_types.h" +#include "DNA_scene_types.h" + +#include "BKE_customdata.h" +#include "BKE_global.h" +#include "BKE_main.h" +#include "BKE_material.h" +#include "BKE_mesh.h" +#include "BKE_object.h" +#include "BKE_utildefines.h" + +#include "radio.h" + +/* locals? not. done in radio.h... */ +/* void rad_addmesh(void); */ +/* void rad_replacemesh(void); */ + +void addaccu(register char *z, register char *t) +{ + register int div, mul; + + mul= *t; + div= mul+1; + (*t)++; + + t[1]= (mul*t[1]+z[1])/div; + t[2]= (mul*t[2]+z[2])/div; + t[3]= (mul*t[3]+z[3])/div; + +} + +void addaccuweight(register char *z, register char *t, int w) +{ + register int div, mul; + + if(w==0) w= 1; + + mul= *t; + div= mul+w; + if(div>255) return; + (*t)= div; + + t[1]= (mul*t[1]+w*z[1])/div; + t[2]= (mul*t[2]+w*z[2])/div; + t[3]= (mul*t[3]+w*z[3])/div; + +} + +void triaweight(Face *face, int *w1, int *w2, int *w3) +{ + float n1[3], n2[3], n3[3], temp; + + n1[0]= face->v2[0]-face->v1[0]; + n1[1]= face->v2[1]-face->v1[1]; + n1[2]= face->v2[2]-face->v1[2]; + n2[0]= face->v3[0]-face->v2[0]; + n2[1]= face->v3[1]-face->v2[1]; + n2[2]= face->v3[2]-face->v2[2]; + n3[0]= face->v1[0]-face->v3[0]; + n3[1]= face->v1[1]-face->v3[1]; + n3[2]= face->v1[2]-face->v3[2]; + Normalize(n1); + Normalize(n2); + Normalize(n3); + temp= 32.0/(PI); + *w1= 0.5+temp*acos(-n1[0]*n3[0]-n1[1]*n3[1]-n1[2]*n3[2]); + *w2= 0.5+temp*acos(-n1[0]*n2[0]-n1[1]*n2[1]-n1[2]*n2[2]); + *w3= 0.5+temp*acos(-n2[0]*n3[0]-n2[1]*n3[1]-n2[2]*n3[2]); + +} + + + +void init_face_tab() +{ + int a= 0; + + if(RG.facebase==0) { + RG.facebase= MEM_callocN(sizeof(void *)*RAD_MAXFACETAB, "init_face_tab"); + } + for(a=0; a<RAD_MAXFACETAB; a++) { + if(RG.facebase[a]==0) break; + MEM_freeN(RG.facebase[a]); + RG.facebase[a]= 0; + } + RG.totface= 0; +} + +Face *addface() +{ + Face *face; + int a; + + if(RG.totface<0 || RG.totface>RAD_MAXFACETAB*1024 ) { + printf("error in addface: %d\n", RG.totface); + return 0; + } + a= RG.totface>>10; + face= RG.facebase[a]; + if(face==0) { + face= MEM_callocN(1024*sizeof(Face),"addface"); + RG.facebase[a]= face; + } + face+= (RG.totface & 1023); + + RG.totface++; + + return face; + +} + +Face * makeface(float *v1, float *v2, float *v3, float *v4, RNode *rn) +{ + Face *face; + + face= addface(); + face->v1= v1; + face->v2= v2; + face->v3= v3; + face->v4= v4; + face->col= rn->col; + face->matindex= rn->par->matindex; + face->orig= rn->orig; + + return face; +} + +void anchorQuadface(RNode *rn, float *v1, float *v2, float *v3, float *v4, int flag) +{ + Face *face; + + switch(flag) { + case 1: + face = makeface(rn->v1, v1, rn->v4, NULL, rn); + face = makeface(v1, rn->v3, rn->v4, NULL, rn); + face = makeface(v1, rn->v2, rn->v3, NULL, rn); + break; + case 2: + face = makeface(rn->v2, v2, rn->v1, NULL, rn); + face = makeface(v2, rn->v4, rn->v1, NULL, rn); + face = makeface(v2, rn->v3, rn->v4, NULL, rn); + break; + case 4: + face = makeface(rn->v3, v3, rn->v2, NULL, rn); + face = makeface(v3, rn->v1, rn->v2, NULL, rn); + face = makeface(v3, rn->v4, rn->v1, NULL, rn); + break; + case 8: + face = makeface(rn->v4, v4, rn->v3, NULL, rn); + face = makeface(v4, rn->v2, rn->v3, NULL, rn); + face = makeface(v4, rn->v1, rn->v2, NULL, rn); + break; + case 3: + face = makeface(rn->v1, v1, rn->v4, NULL, rn); + face = makeface(v1, v2, rn->v4, NULL, rn); + face = makeface(v1, rn->v2, v2, NULL, rn); + face = makeface(v2, rn->v3, rn->v4, NULL, rn); + break; + case 6: + face = makeface(rn->v2, v2, rn->v1, NULL, rn); + face = makeface(v2, v3, rn->v1, NULL, rn); + face = makeface(v2, rn->v3, v3, NULL, rn); + face = makeface(v3, rn->v4, rn->v1, NULL, rn); + break; + case 12: + face = makeface(rn->v3, v3, rn->v2, NULL, rn); + face = makeface(v3, v4, rn->v2, NULL, rn); + face = makeface(v3, rn->v4, v4, NULL, rn); + face = makeface(v4, rn->v1, rn->v2, NULL, rn); + break; + case 9: + face = makeface(rn->v4, v4, rn->v3, NULL, rn); + face = makeface(v4, v1, rn->v3, NULL, rn); + face = makeface(v4, rn->v1, v1, NULL, rn); + face = makeface(v1, rn->v2, rn->v3, NULL, rn); + break; + case 5: + face = makeface(rn->v1, v1, v3, rn->v4, rn); + face = makeface(v1, rn->v2, rn->v3, v3, rn); + break; + case 10: + face = makeface(rn->v1, rn->v2, v2, v4, rn); + face = makeface(v4, v2, rn->v3, rn->v4, rn); + break; + case 7: + face = makeface(rn->v1, v1, v3, rn->v4, rn); + face = makeface(v1, v2, v3, NULL, rn); + face = makeface(v1, rn->v2, v2, NULL, rn); + face = makeface(v2, rn->v3, v3, NULL, rn); + break; + case 14: + face = makeface(rn->v2, v2, v4, rn->v1, rn); + face = makeface(v2, v3, v4, NULL, rn); + face = makeface(v2, rn->v3, v3, NULL, rn); + face = makeface(v3, rn->v4, v4, NULL, rn); + break; + case 13: + face = makeface(rn->v3, v3, v1, rn->v2, rn); + face = makeface(v3, v4, v1, NULL, rn); + face = makeface(v3, rn->v4, v4, NULL, rn); + face = makeface(v4, rn->v1, v1, NULL, rn); + break; + case 11: + face = makeface(rn->v4, v4, v2, rn->v3, rn); + face = makeface(v4, v1, v2, NULL, rn); + face = makeface(v4, rn->v1, v1, NULL, rn); + face = makeface(v1, rn->v2, v2, NULL, rn); + break; + case 15: + face = makeface(v1, v2, v3, v4, rn); + face = makeface(v1, rn->v2, v2, NULL, rn); + face = makeface(v2, rn->v3, v3, NULL, rn); + face = makeface(v3, rn->v4, v4, NULL, rn); + face = makeface(v4, rn->v1, v1, NULL, rn); + break; + } +} + +void anchorTriface(RNode *rn, float *v1, float *v2, float *v3, int flag) +{ + Face *face; + + switch(flag) { + case 1: + face = makeface(rn->v1, v1, rn->v3, NULL, rn); + face = makeface(v1, rn->v2, rn->v3, NULL, rn); + break; + case 2: + face = makeface(rn->v2, v2, rn->v1, NULL, rn); + face = makeface(v2, rn->v3, rn->v1, NULL, rn); + break; + case 4: + face = makeface(rn->v3, v3, rn->v2, NULL, rn); + face = makeface(v3, rn->v1, rn->v2, NULL, rn); + break; + case 3: + face = makeface(rn->v1, v2, rn->v3, NULL, rn); + face = makeface(rn->v1, v1, v2, NULL, rn); + face = makeface(v1, rn->v2, v2, NULL, rn); + break; + case 6: + face = makeface(rn->v2, v3, rn->v1, NULL, rn); + face = makeface(rn->v2, v2, v3, NULL, rn); + face = makeface(v2, rn->v3, v3, NULL, rn); + break; + case 5: + face = makeface(rn->v3, v1, rn->v2, NULL, rn); + face = makeface(rn->v3, v3, v1, NULL, rn); + face = makeface(v3, rn->v1, v1, NULL, rn); + break; + + case 7: + face = makeface(v1, v2, v3, NULL, rn); + face = makeface(rn->v1, v1, v3, NULL, rn); + face = makeface(rn->v2, v2, v1, NULL, rn); + face = makeface(rn->v3, v3, v2, NULL, rn); + break; + } +} + + +float *findmiddlevertex(RNode *node, RNode *nb, float *v1, float *v2) +{ + int test= 0; + + if(nb==0) return 0; + + if(nb->ed1==node) { + if(nb->v1==v1 || nb->v1==v2) test++; + if(nb->v2==v1 || nb->v2==v2) test+=2; + if(test==1) return nb->v2; + else if(test==2) return nb->v1; + } + else if(nb->ed2==node) { + if(nb->v2==v1 || nb->v2==v2) test++; + if(nb->v3==v1 || nb->v3==v2) test+=2; + if(test==1) return nb->v3; + else if(test==2) return nb->v2; + } + else if(nb->ed3==node) { + if(nb->type==4) { + if(nb->v3==v1 || nb->v3==v2) test++; + if(nb->v4==v1 || nb->v4==v2) test+=2; + if(test==1) return nb->v4; + else if(test==2) return nb->v3; + } + else { + if(nb->v3==v1 || nb->v3==v2) test++; + if(nb->v1==v1 || nb->v1==v2) test+=2; + if(test==1) return nb->v1; + else if(test==2) return nb->v3; + } + } + else if(nb->ed4==node) { + if(nb->v4==v1 || nb->v4==v2) test++; + if(nb->v1==v1 || nb->v1==v2) test+=2; + if(test==1) return nb->v1; + else if(test==2) return nb->v4; + } + return 0; +} + +void make_face_tab() /* takes care of anchoring */ +{ + RNode *rn, **el; + Face *face = NULL; + float *v1, *v2, *v3, *v4; + int a, flag, w1, w2, w3; + char *charcol; + + if(RG.totelem==0) return; + + init_face_tab(); + + RG.igamma= 1.0/RG.gamma; + RG.radfactor= RG.radfac*pow(64*64, RG.igamma); + + /* convert face colors */ + el= RG.elem; + for(a=RG.totelem; a>0; a--, el++) { + rn= *el; + charcol= (char *)&( rn->col ); + + charcol[3]= calculatecolor(rn->totrad[0]); + charcol[2]= calculatecolor(rn->totrad[1]); + charcol[1]= calculatecolor(rn->totrad[2]); + } + + /* check nodes and make faces */ + el= RG.elem; + for(a=RG.totelem; a>0; a--, el++) { + + rn= *el; + + rn->v1[3]= 0.0; + rn->v2[3]= 0.0; + rn->v3[3]= 0.0; + if(rn->v4) rn->v4[3]= 0.0; + + /* test edges for subdivide */ + flag= 0; + v1= v2= v3= v4= 0; + if(rn->ed1) { + v1= findmiddlevertex(rn, rn->ed1->down1, rn->v1, rn->v2); + if(v1) flag |= 1; + } + if(rn->ed2) { + v2= findmiddlevertex(rn, rn->ed2->down1, rn->v2, rn->v3); + if(v2) flag |= 2; + } + if(rn->ed3) { + if(rn->type==4) + v3= findmiddlevertex(rn, rn->ed3->down1, rn->v3, rn->v4); + else + v3= findmiddlevertex(rn, rn->ed3->down1, rn->v3, rn->v1); + if(v3) flag |= 4; + } + if(rn->ed4) { + v4= findmiddlevertex(rn, rn->ed4->down1, rn->v4, rn->v1); + if(v4) flag |= 8; + } + + /* using flag and vertexpointers now Faces can be made */ + + if(flag==0) { + makeface(rn->v1, rn->v2, rn->v3, rn->v4, rn); + } + else if(rn->type==4) anchorQuadface(rn, v1, v2, v3, v4, flag); + else anchorTriface(rn, v1, v2, v3, flag); + } + + /* add */ + for(a=0; a<RG.totface; a++) { + + RAD_NEXTFACE(a); + + if(face->v4) { + addaccuweight( (char *)&(face->col), (char *)(face->v1+3), 16 ); + addaccuweight( (char *)&(face->col), (char *)(face->v2+3), 16 ); + addaccuweight( (char *)&(face->col), (char *)(face->v3+3), 16 ); + addaccuweight( (char *)&(face->col), (char *)(face->v4+3), 16 ); + } + else { + triaweight(face, &w1, &w2, &w3); + addaccuweight( (char *)&(face->col), (char *)(face->v1+3), w1 ); + addaccuweight( (char *)&(face->col), (char *)(face->v2+3), w2 ); + addaccuweight( (char *)&(face->col), (char *)(face->v3+3), w3 ); + } + } + +} + +void filterFaces() +{ + /* put vertex colors in faces, and put them back */ + + Face *face = NULL; + int a, w1, w2, w3; + + if(RG.totface==0) return; + + /* clear */ + for(a=0; a<RG.totface; a++) { + RAD_NEXTFACE(a); + face->col= 0; + } + + /* add: vertices with faces */ + for(a=0; a<RG.totface; a++) { + RAD_NEXTFACE(a); + + if(face->v4) { + addaccuweight( (char *)(face->v1+3), (char *)&(face->col), 16 ); + addaccuweight( (char *)(face->v2+3), (char *)&(face->col), 16 ); + addaccuweight( (char *)(face->v3+3), (char *)&(face->col), 16 ); + addaccuweight( (char *)(face->v4+3), (char *)&(face->col), 16 ); + } + else { + triaweight(face, &w1, &w2, &w3); + addaccuweight( (char *)(face->v1+3), (char *)&(face->col), w1 ); + addaccuweight( (char *)(face->v2+3), (char *)&(face->col), w2 ); + addaccuweight( (char *)(face->v3+3), (char *)&(face->col), w3 ); + } + } + + /* clear */ + for(a=0; a<RG.totface; a++) { + RAD_NEXTFACE(a); + face->v1[3]= 0.0; + face->v2[3]= 0.0; + face->v3[3]= 0.0; + if(face->v4) face->v4[3]= 0.0; + } + + + /* add: faces with vertices */ + for(a=0; a<RG.totface; a++) { + + RAD_NEXTFACE(a); + + if(face->v4) { + addaccuweight( (char *)&(face->col), (char *)(face->v1+3), 16 ); + addaccuweight( (char *)&(face->col), (char *)(face->v2+3), 16 ); + addaccuweight( (char *)&(face->col), (char *)(face->v3+3), 16 ); + addaccuweight( (char *)&(face->col), (char *)(face->v4+3), 16 ); + } + else { + triaweight(face, &w1, &w2, &w3); + addaccuweight( (char *)&(face->col), (char *)(face->v1+3), w1 ); + addaccuweight( (char *)&(face->col), (char *)(face->v2+3), w2 ); + addaccuweight( (char *)&(face->col), (char *)(face->v3+3), w3 ); + } + } +} + +void calcfiltrad(RNode *rn, float *cd) +{ + float area; + + cd[0]= 2.0*rn->totrad[0]; + cd[1]= 2.0*rn->totrad[1]; + cd[2]= 2.0*rn->totrad[2]; + area= 2.0; + + if(rn->ed1) { + cd[0]+= rn->ed1->totrad[0]; + cd[1]+= rn->ed1->totrad[1]; + cd[2]+= rn->ed1->totrad[2]; + area+= 1.0; + } + if(rn->ed2) { + cd[0]+= rn->ed2->totrad[0]; + cd[1]+= rn->ed2->totrad[1]; + cd[2]+= rn->ed2->totrad[2]; + area+= 1.0; + } + if(rn->ed3) { + cd[0]+= rn->ed3->totrad[0]; + cd[1]+= rn->ed3->totrad[1]; + cd[2]+= rn->ed3->totrad[2]; + area+= 1.0; + } + if(rn->ed4) { + cd[0]+= rn->ed4->totrad[0]; + cd[1]+= rn->ed4->totrad[1]; + cd[2]+= rn->ed4->totrad[2]; + area+= 1.0; + } + cd[0]/= area; + cd[1]/= area; + cd[2]/= area; + +} + +void filterNodes() +{ + /* colors from nodes in tempblock and back */ + + RNode *rn, **el; + float *coldata, *cd; + int a; + + if(RG.totelem==0) return; + /* the up-nodes need a color */ + el= RG.elem; + for(a=0; a<RG.totelem; a++, el++) { + rn= *el; + if(rn->up) { + rn->up->totrad[0]= 0.0; + rn->up->totrad[1]= 0.0; + rn->up->totrad[2]= 0.0; + if(rn->up->up) { + rn->up->up->totrad[0]= 0.0; + rn->up->up->totrad[1]= 0.0; + rn->up->up->totrad[2]= 0.0; + } + } + } + el= RG.elem; + for(a=0; a<RG.totelem; a++, el++) { + rn= *el; + if(rn->up) { + rn->up->totrad[0]+= 0.5*rn->totrad[0]; + rn->up->totrad[1]+= 0.5*rn->totrad[1]; + rn->up->totrad[2]+= 0.5*rn->totrad[2]; + if(rn->up->up) { + rn->up->up->totrad[0]+= 0.25*rn->totrad[0]; + rn->up->up->totrad[1]+= 0.25*rn->totrad[1]; + rn->up->up->totrad[2]+= 0.25*rn->totrad[2]; + } + } + } + + /* add using area */ + cd= coldata= MEM_mallocN(3*4*RG.totelem, "filterNodes"); + el= RG.elem; + for(a=0; a<RG.totelem; a++, el++) { + calcfiltrad(*el, cd); + cd+= 3; + } + + cd= coldata; + el= RG.elem; + for(a=0; a<RG.totelem; a++, el++) { + rn= *el; + VECCOPY(rn->totrad, cd); + cd+= 3; + } + MEM_freeN(coldata); +} + +void removeEqualNodes(short limit) +{ + /* nodes with equal colors: remove */ + RNode **el, *rn, *rn1; + float thresh, f1, f2; + int a, foundone=1, ok; + int c1, c2; + + if(limit==0) return; + + thresh= 1.0/(256.0*RG.radfactor); + thresh= 3.0*pow(thresh, RG.gamma); + +// XXX waitcursor(1); + + while(foundone) { + foundone= 0; + + el= RG.elem; + for(a=RG.totelem; a>1; a--, el++) { + rn= *el; + rn1= *(el+1); + + if(rn!=rn->par->first && rn1!=rn1->par->first) { + if(rn->up && rn->up==rn1->up) { + f1= rn->totrad[0]+ rn->totrad[1]+ rn->totrad[2]; + f2= rn1->totrad[0]+ rn1->totrad[1]+ rn1->totrad[2]; + + ok= 0; + if(f1<thresh && f2<thresh) ok= 1; + else { + c1= calculatecolor(rn->totrad[0]); + c2= calculatecolor(rn1->totrad[0]); + + if( abs(c1-c2)<=limit ) { + c1= calculatecolor(rn->totrad[1]); + c2= calculatecolor(rn1->totrad[1]); + + if( abs(c1-c2)<=limit ) { + c1= calculatecolor(rn->totrad[2]); + c2= calculatecolor(rn1->totrad[2]); + + if( abs(c1-c2)<=limit ) { + ok= 1; + } + } + } + } + + if(ok) { + rn->up->totrad[0]= 0.5f*(rn->totrad[0]+rn1->totrad[0]); + rn->up->totrad[1]= 0.5f*(rn->totrad[1]+rn1->totrad[1]); + rn->up->totrad[2]= 0.5f*(rn->totrad[2]+rn1->totrad[2]); + rn1= rn->up; + deleteNodes(rn1); + if(rn1->down1) ; + else { + foundone++; + a--; el++; + } + } + } + } + } + if(foundone) { + makeGlobalElemArray(); + } + } +// XXX waitcursor(0); +} + +unsigned int rad_find_or_add_mvert(Mesh *me, MFace *mf, RNode *orignode, float *w, float *radco, GHash *hash) +{ + MVert *mvert = BLI_ghash_lookup(hash, radco); + + if(!mvert) { + mvert = &me->mvert[me->totvert]; + VECCOPY(mvert->co, radco); + me->totvert++; + + BLI_ghash_insert(hash, radco, mvert); + } + + InterpWeightsQ3Dfl(orignode->v1, orignode->v2, orignode->v3, + orignode->v4, mvert->co, w); + + return (unsigned int)(mvert - me->mvert); +} + +void rad_addmesh(Scene *scene) +{ + Face *face = NULL; + Object *ob; + Mesh *me; + MVert *mvert; + MFace *mf; + RNode *node; + Material *ma=0; + GHash *verthash; + unsigned int *mcol; + float cent[3], min[3], max[3], w[4][4]; + int a; + + if(RG.totface==0) + return; + +// if(RG.totmat==MAXMAT) +// XXX notice("warning: cannot assign more than 16 materials to 1 mesh"); + + /* create the mesh */ + ob= add_object(scene, OB_MESH); + + me= ob->data; + me->totvert= totalRadVert(); + me->totface= RG.totface; + me->flag= 0; + + CustomData_add_layer(&me->vdata, CD_MVERT, CD_CALLOC, NULL, me->totvert); + CustomData_add_layer(&me->fdata, CD_MFACE, CD_CALLOC, NULL, me->totface); + CustomData_add_layer(&me->fdata, CD_MCOL, CD_CALLOC, NULL, me->totface); + + CustomData_merge(RG.mfdata, &me->fdata, CD_MASK_MESH, CD_CALLOC, me->totface); + mesh_update_customdata_pointers(me); + + /* create materials and set vertex color flag */ + for(a=0; a<RG.totmat; a++) { + assign_material(ob, RG.matar[a], a+1); + ma= RG.matar[a]; + if(ma) ma->mode |= MA_VERTEXCOL; + } + + /* create vertices and faces in one go, adding vertices to the end of the + mvert array if they were not added already */ + me->totvert= 0; + verthash= BLI_ghash_new(BLI_ghashutil_ptrhash, BLI_ghashutil_ptrcmp); + + mcol= (unsigned int*)me->mcol; + mf= me->mface; + + for(a=0; a<me->totface; a++, mf++, mcol+=4) { + RAD_NEXTFACE(a); + + /* the original node that this node is a subnode of */ + node= RG.mfdatanodes[face->orig]; + + /* set mverts from the radio data, and compute interpolation weights */ + mf->v1= rad_find_or_add_mvert(me, mf, node, w[0], face->v1, verthash); + mf->v2= rad_find_or_add_mvert(me, mf, node, w[1], face->v2, verthash); + mf->v3= rad_find_or_add_mvert(me, mf, node, w[2], face->v3, verthash); + if(face->v4) + mf->v4= rad_find_or_add_mvert(me, mf, node, w[3], face->v4, verthash); + + /* copy face and interpolate data */ + mf->mat_nr= face->matindex; + + CustomData_copy_data(RG.mfdata, &me->fdata, face->orig, a, 1); + CustomData_interp(RG.mfdata, &me->fdata, &face->orig, NULL, (float*)w, 1, a); + + /* load face vertex colors, with alpha added */ + mcol[0]= *((unsigned int*)face->v1+3) | 0x1000000; + mcol[1]= *((unsigned int*)face->v2+3) | 0x1000000; + mcol[2]= *((unsigned int*)face->v3+3) | 0x1000000; + if(face->v4) + mcol[3]= *((unsigned int*)face->v4+3) | 0x1000000; + + /* reorder face indices if needed to make face->v4 == 0 */ + test_index_face(mf, &me->fdata, a, face->v4? 4: 3); + } + + BLI_ghash_free(verthash, NULL, NULL); + + /* boundbox and center new */ + INIT_MINMAX(min, max); + + mvert= me->mvert; + for(a=0; a<me->totvert; a++, mvert++) { + DO_MINMAX(mvert->co, min, max); + } + + cent[0]= (min[0]+max[0])/2.0f; + cent[1]= (min[1]+max[1])/2.0f; + cent[2]= (min[2]+max[2])/2.0f; + + mvert= me->mvert; + for(a=0; a<me->totvert; a++, mvert++) { + VecSubf(mvert->co, mvert->co, cent); + } + + VECCOPY(ob->loc, cent); + + /* create edges */ + make_edges(me, 0); +} + +void rad_replacemesh(Scene *scene) +{ + RPatch *rp; + +// XXX deselectall(); + + rp= RG.patchbase.first; + while(rp) { + if( exist_object(rp->from)) { + if (rp->from->type == OB_MESH) { + rp->from->flag |= SELECT; + } + } + rp= rp->next; + } + + copy_objectflags(scene); +// XXX delete_obj(1); + + rad_addmesh(scene); +} + diff --git a/source/blender/radiosity/intern/source/radpreprocess.c b/source/blender/radiosity/intern/source/radpreprocess.c new file mode 100644 index 00000000000..2b3ce1a856b --- /dev/null +++ b/source/blender/radiosity/intern/source/radpreprocess.c @@ -0,0 +1,828 @@ + /* *************************************** + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + + + + preproces.c nov/dec 1992 + may 1999 + + - collect from meshes + - countglobaldata() + - makeGlobalElemArray() + + $Id$ + + *************************************** */ + +#include <stdlib.h> +#include <stdio.h> +#include <string.h> +#include <math.h> + +#include "MEM_guardedalloc.h" + +#include "BLI_blenlib.h" +#include "BLI_arithb.h" + +#include "DNA_mesh_types.h" +#include "DNA_meshdata_types.h" +#include "DNA_object_types.h" +#include "DNA_scene_types.h" +#include "DNA_view3d_types.h" + +#include "BKE_customdata.h" +#include "BKE_global.h" +#include "BKE_main.h" +#include "BKE_material.h" +#include "BKE_mesh.h" +#include "BKE_object.h" /* during_script() */ +#include "BKE_utildefines.h" + +#include "radio.h" + +#include "BLO_sys_types.h" // for intptr_t support + +void setparelem(RNode *rn, RPatch *par); + +void splitconnected() +{ + /* Since input meshes can have faces with sharing vertices, the geometry is being tested here. + * Using normals and colors, faces are split separately. we do this by storing for each + * vertex a normal and a color + */ + RPatch *rp; + RNode *rn; + VeNoCo *vnc, *next, *vnc1; + int a; + + /* test if we need a split */ + + rp= RG.patchbase.first; + while(rp) { + rn= rp->first; + if((rp->f1 & RAD_NO_SPLIT)==0) { + for(a=0; a<rp->type; a++) { + + if(a==0) vnc= (VeNoCo *)rn->v1; + else if(a==1) vnc= (VeNoCo *)rn->v2; + else if(a==2) vnc= (VeNoCo *)rn->v3; + else vnc= (VeNoCo *)rn->v4; + + if(vnc->flag==0) { + vnc->n= (float *)rp->norm; + vnc->col= (float *)rp->ref; + vnc->flag= 1; + } + else { /* is face from this vertex allowed for gouraud? */ + vnc1= vnc; + while(vnc1) { + if(VecCompare(vnc1->n, rp->norm, 0.01f)) { + if(VecCompare(vnc1->col, rp->ref, 0.01f)) { + break; + } + } + vnc= vnc1; + vnc1= vnc1->next; + } + if(vnc1==0) { + vnc1= MEM_mallocN(sizeof(VeNoCo), "splitconn"); + vnc1->next= 0; + vnc1->v= mallocVert(); + vnc->next= vnc1; + VECCOPY(vnc1->v, vnc->v); + vnc1->n= (float *)rp->norm; + vnc1->col= (float *)rp->ref; + } + if(a==0) rn->v1= (float *)vnc1; + else if(a==1) rn->v2= (float *)vnc1; + else if(a==2) rn->v3= (float *)vnc1; + else rn->v4= (float *)vnc1; + } + } + } + rp= rp->next; + } + /* adapt vertexpointers from nodes */ + + rp= RG.patchbase.first; + while(rp) { + rn= rp->first; + rn->v1= ((VeNoCo *)(rn->v1))->v; + rn->v2= ((VeNoCo *)(rn->v2))->v; + rn->v3= ((VeNoCo *)(rn->v3))->v; + if(rp->type==4) rn->v4= ((VeNoCo *)(rn->v4))->v; + + rp= rp->next; + } + + + /* free all */ + vnc= RG.verts; + for(a=0; a<RG.totvert; a++) { + vnc1= vnc->next; + while(vnc1) { + next= vnc1->next; + MEM_freeN(vnc1); + vnc1= next; + } + vnc++; + } + MEM_freeN(RG.verts); + RG.verts= 0; +} + +int vergedge(const void *v1,const void *v2) +{ + int *e1, *e2; + + e1= (int *)v1; + e2= (int *)v2; + + if( e1[0] > e2[0] ) return 1; + else if( e1[0] < e2[0] ) return -1; + else if( e1[1] > e2[1] ) return 1; + else if( e1[1] < e2[1] ) return -1; + + return 0; +} + + +void addedge(float *v1, float *v2, EdSort *es) +{ + if( ((intptr_t)v1)<((intptr_t)v2) ) { + es->v1= v1; + es->v2= v2; + } + else { + es->v2= v1; + es->v1= v2; + } +} + +static void setedge(RNode *node, RNode *nb, int nr, int nrb) +{ + switch(nr) { + case 1: + node->ed1= nb; + break; + case 2: + node->ed2= nb; + break; + case 3: + node->ed3= nb; + break; + case 4: + node->ed4= nb; + break; + } + switch(nrb) { + case 1: + nb->ed1= node; + break; + case 2: + nb->ed2= node; + break; + case 3: + nb->ed3= node; + break; + case 4: + nb->ed4= node; + break; + } +} + +void setedgepointers() +{ + /* make edge-array and sort it */ + /* pairs of edges are put together: fill in pointers in nodes */ + EdSort *es, *esblock; + RPatch *rp; + RNode *rn; + int tot= 0; + + rp= RG.patchbase.first; + while(rp) { + tot+= rp->type; + rp= rp->next; + } + + if(tot==0) return; + + es=esblock= MEM_mallocN(tot*sizeof(EdSort), "setedgepointers"); + rp= RG.patchbase.first; + while(rp) { + rn= rp->first; + addedge(rn->v1, rn->v2, es); + es->nr= 1; + es->node= rn; + es++; + addedge(rn->v2, rn->v3, es); + es->nr= 2; + es->node= rn; + es++; + if(rp->type==3) { + addedge(rn->v3, rn->v1, es); + es->nr= 3; + es->node= rn; + es++; + } + else { + addedge(rn->v3, rn->v4, es); + es->nr= 3; + es->node= rn; + es++; + addedge(rn->v4, rn->v1, es); + es->nr= 4; + es->node= rn; + es++; + } + rp= rp->next; + } + + qsort(esblock,tot,sizeof(EdSort),vergedge); + + es= esblock; + while(tot>0) { + if( es->v1== (es+1)->v1 ) { + if( es->v2== (es+1)->v2 ) { + setedge(es->node, (es+1)->node, es->nr, (es+1)->nr); + tot--; + es++; + } + } + es++; + tot--; + } + + MEM_freeN(esblock); +} + +static int materialIndex(Material *ma) +{ + int i = 0; + for(i=0;i< RG.totmat; i++) + { + if (RG.matar[i] == ma) { + return i; + } + } + return -1; +} + +void rad_collect_meshes(Scene *scene, View3D *v3d) +{ + extern Material defmaterial; + Base *base; + Object *ob; + Mesh *me; + MVert *mvert; + MFace *mface; + MTFace *tf, *tface; + Material *ma = NULL, *noma= NULL; + RPatch *rp; + RNode *rn; + VeNoCo *vnc, **nodevert; + float *vd, *v1, *v2, *v3, *v4 = NULL; + int a, b, offs, index, mfdatatot; + + if (v3d==NULL) { + printf("Error, trying to collect radiosity meshes with no 3d view\n"); + return; + } + + set_radglobal(scene); + + freeAllRad(scene); + + start_fastmalloc("Radiosity"); + + /* count the number of verts */ + RG.totvert= 0; + RG.totface= 0; + base= (scene->base.first); + while(base) { + if(((base)->flag & SELECT) && ((base)->lay & v3d->lay) ) { + if(base->object->type==OB_MESH) { + base->flag |= OB_RADIO; + me= base->object->data; + RG.totvert+= me->totvert; + } + } + base= base->next; + } + if(RG.totvert==0) { + if (!during_script()); //XXX error("No vertices"); + return; + } + vnc= RG.verts= MEM_callocN(RG.totvert*sizeof(VeNoCo), "radioverts"); + + RG.min[0]= RG.min[1]= RG.min[2]= 1.0e20f; + RG.max[0]= RG.max[1]= RG.max[2]= -1.0e20f; + + mfdatatot= 0; + + /* min-max and material array */ + base= (scene->base.first); + while(base) { + if( ((base)->flag & SELECT) && ((base)->lay & v3d->lay) ) { + if(base->object->type==OB_MESH) { + me= base->object->data; + mvert= me->mvert; + for(a=0; a<me->totvert; a++, mvert++) { + vd= mallocVert(); + VECCOPY(vd, mvert->co); + /* Should make MTC its own module... */ + Mat4MulVecfl(base->object->obmat, vd); + + vnc->v= vd; + for(b=0; b<3; b++) { + RG.min[b]= MIN2(RG.min[b], vd[b]); + RG.max[b]= MAX2(RG.max[b], vd[b]); + } + vnc++; + } + + if(base->object->totcol==0) { + if(RG.totmat<MAXMAT) { + if(noma==NULL) { + noma= add_material("RadioMat"); + RG.matar[RG.totmat]= noma; + RG.totmat++; + } + } + } + else { + for(a=0; a<base->object->totcol; a++) { + if(RG.totmat >= MAXMAT) break; + + ma = give_current_material(base->object, a+1); + + if (materialIndex(ma)!=-1) break; + + RG.matar[RG.totmat]= ma; + RG.totmat++; + } + } + + mfdatatot += me->totface; + } + } + base= base->next; + } + + RG.cent[0]= (RG.min[0]+ RG.max[0])/2; + RG.cent[1]= (RG.min[1]+ RG.max[1])/2; + RG.cent[2]= (RG.min[2]+ RG.max[2])/2; + RG.size[0]= (RG.max[0]- RG.min[0]); + RG.size[1]= (RG.max[1]- RG.min[1]); + RG.size[2]= (RG.max[2]- RG.min[2]); + RG.maxsize= MAX3(RG.size[0],RG.size[1],RG.size[2]); + + RG.mfdata= MEM_callocN(sizeof(CustomData), "radiomfdata"); + RG.mfdatanodes= MEM_mallocN(sizeof(RNode*)*mfdatatot, "radiomfdatanodes"); + RG.mfdatatot= mfdatatot; + + /* make patches */ + + RG.totelem= 0; + RG.totpatch= 0; + RG.totlamp= 0; + offs= 0; + + base= (scene->base.first); + while(base) { + if( ((base)->flag & SELECT) && ((base)->lay & v3d->lay) ) { + if(base->object->type==OB_MESH) { + ob= base->object; + me= ob->data; + mface= me->mface; + tface= me->mtface; + + index= -1; + + CustomData_merge(&me->fdata, RG.mfdata, CD_MASK_DERIVEDMESH, + CD_DEFAULT, mfdatatot); + + for(a=0; a<me->totface; a++, mface++) { + tf= tface? tface+a: NULL; + + if (tf && (tf->mode & TF_INVISIBLE)) + continue; + + rp= callocPatch(); + BLI_addtail(&(RG.patchbase), rp); + rp->from= ob; + + if(mface->v4) rp->type= 4; + else rp->type= 3; + + rp->first= rn= callocNode(); + + if(mface->flag & ME_SMOOTH) rp->f1= RAD_NO_SPLIT; + + /* temporal: we store the venoco in the node */ + rn->v1= (float *)(RG.verts+mface->v1+offs); + v1= (RG.verts+mface->v1+offs)->v; + rn->v2= (float *)(RG.verts+mface->v2+offs); + v2= (RG.verts+mface->v2+offs)->v; + rn->v3= (float *)(RG.verts+mface->v3+offs); + v3= (RG.verts+mface->v3+offs)->v; + + if(mface->v4) { + rn->v4= (float *)(RG.verts+mface->v4+offs); + v4= (RG.verts+mface->v4+offs)->v; + } + rn->par= rp; + rn->f= RAD_PATCH; /* this node is a Patch */ + rn->type= rp->type; + + if(rn->type==4) { + rp->area= AreaQ3Dfl(v1, v2, v3, v4); + CalcNormFloat4(v1, v2, v3, v4, rp->norm); + } + else { + rp->area= AreaT3Dfl(v1, v2, v3); + CalcNormFloat(v1, v2, v3, rp->norm); + } + + rn->area= rp->area; + + /* color and emit */ + if(mface->mat_nr != index) { + index= mface->mat_nr; + ma= give_current_material(ob, index+1); + if(ma==0) ma= &defmaterial; + } + rp->ref[0]= ma->r; + rp->ref[1]= ma->g; + rp->ref[2]= ma->b; + + if(ma->emit) RG.totlamp++; + + rp->emit[0]= rp->emit[1]= rp->emit[2]= ma->emit; + rp->emit[0]*= rp->ref[0]; + rp->emit[1]*= rp->ref[1]; + rp->emit[2]*= rp->ref[2]; + +// uncommented, this is not satisfying, but i leave it in code for now (ton) +// if(ma->translucency!=0.0) rn->f |= RAD_TWOSIDED; + + nodevert= (VeNoCo **)&(rn->v1); + for(b=0; b<rp->type; b++) { + rp->cent[0]+= (*nodevert)->v[0]; + rp->cent[1]+= (*nodevert)->v[1]; + rp->cent[2]+= (*nodevert)->v[2]; + nodevert++; + } + rp->cent[0]/= (float)rp->type; + rp->cent[1]/= (float)rp->type; + rp->cent[2]/= (float)rp->type; + + /* for reconstruction materials */ + rp->matindex= materialIndex(ma); + if(rp->matindex==-1) rp->matindex= 1; + + /* these RNode's are stored now for later use in rad_addmesh + they should not get deleted before that */ + rn->orig= RG.totelem; + RG.mfdatanodes[RG.totelem]= rn; + + CustomData_copy_data(&me->fdata, RG.mfdata, a, RG.totelem, 1); + + RG.totelem++; + RG.totpatch++; + } + + offs+= me->totvert; + } + } + base= base->next; + } + + splitconnected(); + setedgepointers(); + + makeGlobalElemArray(); + pseudoAmb(); + rad_setlimits(scene); +} + +void setparelem(RNode *rn, RPatch *par) +{ + + if(rn->down1) { + setparelem(rn->down1, par); + setparelem(rn->down2, par); + } + else { + rn->par= par; + } +} + +void countelem(RNode *rn) +{ + + if(rn->down1) { + countelem(rn->down1); + countelem(rn->down2); + } + else RG.totelem++; +} + +void countglobaldata() +{ + /* counts elements and patches*/ + RPatch *rp; + + RG.totelem= RG.totpatch= 0; + + rp= RG.patchbase.first; + while(rp) { + RG.totpatch++; + countelem(rp->first); + rp= rp->next; + } +} + +void addelem(RNode ***el, RNode *rn, RPatch *rp) +{ + if(rn->down1) { + addelem(el, rn->down1, rp); + addelem(el, rn->down2, rp); + } + else { + rn->par= rp; + **el= rn; + (*el)++; + } +} + +void makeGlobalElemArray() +{ + /* always called when # of elements change */ + RPatch *rp; + RNode **el; + + countglobaldata(); + + if(RG.elem) MEM_freeN(RG.elem); + if(RG.totelem) { + el= RG.elem= MEM_mallocN(sizeof(void *)*RG.totelem, "makeGlobalElemArray"); + } + else { + RG.elem= 0; + return; + } + + /* recursive adding elements */ + rp= RG.patchbase.first; + while(rp) { + addelem(&el, rp->first, rp); + rp= rp->next; + } + + /* formfactor array */ + if(RG.formfactors) MEM_freeN(RG.formfactors); + if(RG.totelem) + RG.formfactors= MEM_mallocN(sizeof(float)*RG.totelem, "formfactors"); + else + RG.formfactors= 0; +} + +void splitpatch(RPatch *old) /* in case of overflow during shoot */ +{ + RNode *rn; + float **fpp; + RPatch *rp; + int a; + + rn= old->first; + if(rn->down1==0) return; + rn= rn->down1; + + old->unshot[0]/=2.0; + old->unshot[1]/=2.0; + old->unshot[2]/=2.0; + setnodeflags(old->first, 2, 0); + + rp= mallocPatch(); + *rp= *old; + BLI_addhead(&RG.patchbase, rp); + rp->first= rn; + rp->area= rn->area; + rp->cent[0]= rp->cent[1]= rp->cent[2]= 0.0; + fpp= &(rn->v1); + for(a=0; a<rp->type; a++) { + rp->cent[0]+= (*fpp)[0]; + rp->cent[1]+= (*fpp)[1]; + rp->cent[2]+= (*fpp)[2]; + fpp++; + } + rp->cent[0]/=(float)rp->type; + rp->cent[1]/=(float)rp->type; + rp->cent[2]/=(float)rp->type; + + setparelem(rn, rp); + + rn= old->first->down2; + + rp= mallocPatch(); + *rp= *old; + BLI_addhead(&RG.patchbase, rp); + rp->first= rn; + rp->area= rn->area; + rp->cent[0]= rp->cent[1]= rp->cent[2]= 0.0; + fpp= &(rn->v1); + for(a=0; a<rp->type; a++) { + rp->cent[0]+= (*fpp)[0]; + rp->cent[1]+= (*fpp)[1]; + rp->cent[2]+= (*fpp)[2]; + fpp++; + } + rp->cent[0]/=(float)rp->type; + rp->cent[1]/=(float)rp->type; + rp->cent[2]/=(float)rp->type; + + setparelem(rn, rp); + + BLI_remlink(&RG.patchbase, old); + freePatch(old); +} + + +void addpatch(RPatch *old, RNode *rn) +{ + float **fpp; + RPatch *rp; + int a; + + if(rn->down1) { + addpatch(old, rn->down1); + addpatch(old, rn->down2); + } + else { + rp= mallocPatch(); + *rp= *old; + BLI_addhead(&RG.patchbase, rp); + rp->first= rn; + + rp->area= rn->area; + rp->cent[0]= rp->cent[1]= rp->cent[2]= 0.0; + fpp= &(rn->v1); + for(a=0; a<rp->type; a++) { + rp->cent[0]+= (*fpp)[0]; + rp->cent[1]+= (*fpp)[1]; + rp->cent[2]+= (*fpp)[2]; + fpp++; + } + rp->cent[0]/=(float)rp->type; + rp->cent[1]/=(float)rp->type; + rp->cent[2]/=(float)rp->type; + + rn->par= rp; + } +} + +void converttopatches() +{ + /* chacks patches list, if node subdivided: new patch */ + RPatch *rp, *next; + + rp= RG.patchbase.first; + while(rp) { + next= rp->next; + if(rp->first->down1) { + addpatch(rp, rp->first); + BLI_remlink(&RG.patchbase, rp); + freePatch(rp); + } + rp= next; + } + +} + +void subdiv_elements() +{ + RNode **el, *rn; + int a, toobig= 1; + + rad_init_energy(); + + /* first maxsize elements */ + + while(toobig) { + toobig= 0; + + el= RG.elem; + for(a=RG.totelem; a>0; a--, el++) { + rn= *el; + if( rn->totrad[0]==0.0 && rn->totrad[1]==0.0 && rn->totrad[2]==0.0) { + if(rn->area>RG.elemmin) { + subdivideNode(rn, 0); + if(rn->down1 ) { + toobig= 1; + if(rn->down1->area>RG.elemmin) + subdivideNode( rn->down1, 0); + if(rn->down2->area>RG.elemmin) + subdivideNode( rn->down2, 0); + } + } + } + } + if(toobig) makeGlobalElemArray(); + } + + el= RG.elem; + for(a=RG.totelem; a>0; a--, el++) { + rn= *el; + if( rn->totrad[0]==0.0 && rn->totrad[1]==0.0 && rn->totrad[2]==0.0) { + subdivideNode(rn, 0); + if( rn->down1 ) { + subdivideNode( rn->down1, 0); + subdivideNode( rn->down2, 0); + } + } + } + makeGlobalElemArray(); +} + +void subdividelamps() +{ + RPatch *rp, *next; + + rp= RG.patchbase.first; + while(rp) { + next= rp->next; + if(rp->emit[0]!=0.0 || rp->emit[1]!=0.0 || rp->emit[2]!=0.0) { + subdivideNode( rp->first, 0); + if(rp->first->down1) { + subdivideNode(rp->first->down1, 0); + subdivideNode(rp->first->down2, 0); + } + + addpatch(rp, rp->first); + BLI_remlink(&RG.patchbase, rp); + freePatch(rp); + } + rp= next; + } + +} + +void maxsizePatches() +{ + RPatch *rp; + int toobig= 1; + + while(toobig) { + toobig= 0; + rp= RG.patchbase.first; + while(rp) { + if(rp->area>RG.patchmax) { + subdivideNode( rp->first, 0); + if(rp->first->down1) toobig= 1; + } + rp= rp->next; + } + + if(toobig) converttopatches(); + } + + /* count lamps */ + rp= RG.patchbase.first; + RG.totlamp= 0; + while(rp) { + if(rp->emit[0]!=0.0 || rp->emit[1]!=0.0 || rp->emit[2]!=0.0) { + RG.totlamp++; + } + rp= rp->next; + } + makeGlobalElemArray(); +} + + + diff --git a/source/blender/radiosity/intern/source/radrender.c b/source/blender/radiosity/intern/source/radrender.c new file mode 100644 index 00000000000..d33bbc90ee3 --- /dev/null +++ b/source/blender/radiosity/intern/source/radrender.c @@ -0,0 +1,530 @@ +/* *************************************** + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ + +/* radrender.c, aug 2003 + * + * Most of the code here is copied from radiosity code, to optimize for renderfaces. + * Shared function calls mostly reside in radfactors.c + * No adaptive subdivision takes place + * + * - do_radio_render(); main call, extern + * - initradfaces(); add radface structs in render faces, init radio globals + * - + * - initradiosity(); LUTs + * - inithemiwindows(); + * - progressiverad(); main itteration loop + * - hemi zbuffers + * - calc rad factors + * + * - closehemiwindows(); + * - freeAllRad(); + * - make vertex colors + * + * - during render, materials use totrad as ambient replacement + * - free radfaces + */ + +#include <stdlib.h> +#include <string.h> +#include <math.h> + +#include "MEM_guardedalloc.h" + +#include "BLI_blenlib.h" +#include "BLI_arithb.h" +#include "BLI_rand.h" + +#include "BKE_utildefines.h" +#include "BKE_global.h" +#include "BKE_main.h" + +#include "radio.h" + +/* the radiosity module uses internal includes from render! */ +#include "renderpipeline.h" +#include "render_types.h" +#include "renderdatabase.h" + + +/* only needed now for a print, if its useful move to RG */ +static float maxenergy; + +/* find the face with maximum energy to become shooter */ +/* nb: _rr means rad-render version of existing radio call */ +static void findshoot_rr(Render *re, VlakRen **shoot_p, RadFace **shootrf_p) +{ + RadFace *rf, *shootrf, **radface; + ObjectRen *obr; + VlakRen *vlr=NULL, *shoot; + float energy; + int a; + + shoot= NULL; + shootrf= NULL; + maxenergy= 0.0; + + for(obr=re->objecttable.first; obr; obr=obr->next) { + for(a=0; a<obr->totvlak; a++) { + if((a & 255)==0) vlr= obr->vlaknodes[a>>8].vlak; else vlr++; + if((radface=RE_vlakren_get_radface(obr, vlr, 0)) && *radface) { + rf= *radface; + rf->flag &= ~RAD_SHOOT; + + energy= rf->unshot[0]*rf->area; + energy+= rf->unshot[1]*rf->area; + energy+= rf->unshot[2]*rf->area; + + if(energy>maxenergy) { + shoot= vlr; + shootrf= rf; + maxenergy= energy; + } + } + } + } + + if(shootrf) { + maxenergy/= RG.totenergy; + if(maxenergy<RG.convergence) { + *shoot_p= NULL; + *shootrf_p= NULL; + return; + } + shootrf->flag |= RAD_SHOOT; + } + + *shoot_p= shoot; + *shootrf_p= shootrf; +} + +static void backface_test_rr(Render *re, VlakRen *shoot, RadFace *shootrf) +{ + ObjectRen *obr; + VlakRen *vlr=NULL; + RadFace *rf, **radface; + float tvec[3]; + int a; + + /* backface testing */ + for(obr=re->objecttable.first; obr; obr=obr->next) { + for(a=0; a<obr->totvlak; a++) { + if((a & 255)==0) vlr= obr->vlaknodes[a>>8].vlak; else vlr++; + if(vlr != shoot && (radface=RE_vlakren_get_radface(obr, vlr, 0)) && *radface) { + rf= *radface; + VecSubf(tvec, shootrf->cent, rf->cent); + + if(tvec[0]*rf->norm[0]+ tvec[1]*rf->norm[1]+ tvec[2]*rf->norm[2] < 0.0) + rf->flag |= RAD_BACKFACE; + } + } + } +} + +static void clear_backface_test_rr(Render *re) +{ + ObjectRen *obr; + VlakRen *vlr=NULL; + RadFace *rf, **radface; + int a; + + /* backface flag clear */ + for(obr=re->objecttable.first; obr; obr=obr->next) { + for(a=0; a<obr->totvlak; a++) { + if((a & 255)==0) vlr= obr->vlaknodes[a>>8].vlak; else vlr++; + + if((radface=RE_vlakren_get_radface(obr, vlr, 0)) && *radface) { + rf= *radface; + rf->flag &= ~RAD_BACKFACE; + } + } + } +} + +extern RadView hemitop, hemiside; // radfactors.c + +/* hemi-zbuffering, delivers formfactors array */ +static void makeformfactors_rr(Render *re, VlakRen *shoot, RadFace *shootrf) +{ + ObjectRen *obr; + VlakRen *vlr=NULL; + RadFace *rf, **radface; + float len, vec[3], up[3], side[3], tar[5][3], *fp; + int a; + + memset(RG.formfactors, 0, sizeof(float)*RG.totelem); + + /* set up hemiview */ + /* first: upvector for hemitop, we use diagonal hemicubes to prevent aliasing */ + + VecSubf(vec, shoot->v1->co, shootrf->cent); + Crossf(up, shootrf->norm, vec); + len= Normalize(up); + + VECCOPY(hemitop.up, up); + VECCOPY(hemiside.up, shootrf->norm); + + Crossf(side, shootrf->norm, up); + + /* five targets */ + VecAddf(tar[0], shootrf->cent, shootrf->norm); + VecAddf(tar[1], shootrf->cent, up); + VecSubf(tar[2], shootrf->cent, up); + VecAddf(tar[3], shootrf->cent, side); + VecSubf(tar[4], shootrf->cent, side); + + /* camera */ + VECCOPY(hemiside.cam, shootrf->cent); + VECCOPY(hemitop.cam, shootrf->cent); + + /* do it! */ + VECCOPY(hemitop.tar, tar[0]); + hemizbuf(&hemitop); + + for(a=1; a<5; a++) { + VECCOPY(hemiside.tar, tar[a]); + hemizbuf(&hemiside); + } + + /* convert factors to real radiosity */ + fp= RG.formfactors; + + for(obr=re->objecttable.first; obr; obr=obr->next) { + for(a=0; a<obr->totvlak; a++) { + if((a & 255)==0) vlr= obr->vlaknodes[a>>8].vlak; else vlr++; + + if((radface=RE_vlakren_get_radface(obr, vlr, 0)) && *radface) { + rf= *radface; + if(*fp!=0.0 && rf->area!=0.0) { + *fp *= shootrf->area/rf->area; + if(*fp>1.0) *fp= 1.0001; + } + fp++; + } + } + } +} + +/* based at RG.formfactors array, distribute shoot energy over other faces */ +static void applyformfactors_rr(Render *re, VlakRen *shoot, RadFace *shootrf) +{ + ObjectRen *obr; + VlakRen *vlr=NULL; + RadFace *rf, **radface; + float *fp, *ref, unr, ung, unb, r, g, b; + int a; + + unr= shootrf->unshot[0]; + ung= shootrf->unshot[1]; + unb= shootrf->unshot[2]; + + fp= RG.formfactors; + + for(obr=re->objecttable.first; obr; obr=obr->next) { + for(a=0; a<obr->totvlak; a++) { + if((a & 255)==0) vlr= obr->vlaknodes[a>>8].vlak; else vlr++; + + if((radface=RE_vlakren_get_radface(obr, vlr, 0)) && *radface) { + rf= *radface; + if(*fp!= 0.0) { + + ref= &(vlr->mat->r); + + r= (*fp)*unr*ref[0]; + g= (*fp)*ung*ref[1]; + b= (*fp)*unb*ref[2]; + + // if(rf->flag & RAD_BACKFACE) { + + rf->totrad[0]+= r; + rf->totrad[1]+= g; + rf->totrad[2]+= b; + + rf->unshot[0]+= r; + rf->unshot[1]+= g; + rf->unshot[2]+= b; + } + fp++; + } + } + } + /* shoot energy has been shot */ + shootrf->unshot[0]= shootrf->unshot[1]= shootrf->unshot[2]= 0.0; +} + + +/* main loop for itterations */ +static void progressiverad_rr(Render *re) +{ + VlakRen *shoot; + RadFace *shootrf; + float unshot[3]; + int it= 0; + + findshoot_rr(re, &shoot, &shootrf); + while( shoot ) { + + /* backfaces receive no energy, but are zbuffered... */ + backface_test_rr(re, shoot, shootrf); + + /* ...unless it's two sided */ + if(shootrf->flag & RAD_TWOSIDED) { + VECCOPY(unshot, shootrf->unshot); + VecNegf(shootrf->norm); + makeformfactors_rr(re, shoot, shootrf); + applyformfactors_rr(re, shoot, shootrf); + VecNegf(shootrf->norm); + VECCOPY(shootrf->unshot, unshot); + } + + /* hemi-zbuffers */ + makeformfactors_rr(re, shoot, shootrf); + /* based at RG.formfactors array, distribute shoot energy over other faces */ + applyformfactors_rr(re, shoot, shootrf); + + it++; + re->timecursor(re->tch, it); + + clear_backface_test_rr(re); + + if(re->test_break(re->tbh)) break; + if(RG.maxiter && RG.maxiter<=it) break; + + findshoot_rr(re, &shoot, &shootrf); + } + printf(" Unshot energy:%f\n", 1000.0*maxenergy); + + re->timecursor(re->tch, re->scene->r.cfra); +} + +static RadFace *radfaces=NULL; + +static void initradfaces(Render *re) +{ + ObjectRen *obr; + VlakRen *vlr= NULL; + RadFace *rf, **radface; + int a, b; + + /* globals */ + RG.totenergy= 0.0; + RG.totpatch= 0; // we count initial emittors here + RG.totelem= 0; // total # faces are put here (so we can use radfactors.c calls) + /* size is needed for hemicube clipping */ + RG.min[0]= RG.min[1]= RG.min[2]= 1.0e20; + RG.max[0]= RG.max[1]= RG.max[2]= -1.0e20; + + /* count first for fast malloc */ + for(obr=re->objecttable.first; obr; obr=obr->next) { + for(a=0; a<obr->totvlak; a++) { + if((a & 255)==0) vlr= obr->vlaknodes[a>>8].vlak; else vlr++; + + if(vlr->mat->mode & MA_RADIO) { + if(vlr->mat->emit > 0.0) { + RG.totpatch++; + } + RG.totelem++; + } + } + } + +printf(" Rad elems: %d emittors %d\n", RG.totelem, RG.totpatch); + if(RG.totelem==0 || RG.totpatch==0) return; + + /* make/init radfaces */ + rf=radfaces= MEM_callocN(RG.totelem*sizeof(RadFace), "radfaces"); + for(obr=re->objecttable.first; obr; obr=obr->next) { + for(a=0; a<obr->totvlak; a++) { + if((a & 255)==0) vlr= obr->vlaknodes[a>>8].vlak; else vlr++; + + if(vlr->mat->mode & MA_RADIO) { + + /* during render, vlr->n gets flipped/corrected, we cannot have that */ + if (obr->ob->transflag & OB_NEG_SCALE){ + /* The object has negative scale that will cause the normals to flip. + To counter this unwanted normal flip, swap vertex 2 and 4 for a quad + or vertex 2 and 3 (see flip_face) for a triangle in the call to CalcNormFloat4 + in order to flip the normals back to the way they were in the original mesh. */ + if(vlr->v4) CalcNormFloat4(vlr->v1->co, vlr->v4->co, vlr->v3->co, vlr->v2->co, rf->norm); + else CalcNormFloat(vlr->v1->co, vlr->v3->co, vlr->v2->co, rf->norm); + }else{ + if(vlr->v4) CalcNormFloat4(vlr->v1->co, vlr->v2->co, vlr->v3->co, vlr->v4->co, rf->norm); + else CalcNormFloat(vlr->v1->co, vlr->v2->co, vlr->v3->co, rf->norm); + } + + rf->totrad[0]= vlr->mat->emit*vlr->mat->r; + rf->totrad[1]= vlr->mat->emit*vlr->mat->g; + rf->totrad[2]= vlr->mat->emit*vlr->mat->b; + VECCOPY(rf->unshot, rf->totrad); + + if(vlr->v4) { + rf->area= AreaQ3Dfl(vlr->v1->co, vlr->v2->co, vlr->v3->co, vlr->v4->co); + CalcCent4f(rf->cent, vlr->v1->co, vlr->v2->co, vlr->v3->co, vlr->v4->co); + } + else { + rf->area= AreaT3Dfl(vlr->v1->co, vlr->v2->co, vlr->v3->co); + CalcCent3f(rf->cent, vlr->v1->co, vlr->v2->co, vlr->v3->co); + } + + RG.totenergy+= rf->unshot[0]*rf->area; + RG.totenergy+= rf->unshot[1]*rf->area; + RG.totenergy+= rf->unshot[2]*rf->area; + + for(b=0; b<3; b++) { + RG.min[b]= MIN2(RG.min[b], rf->cent[b]); + RG.max[b]= MAX2(RG.max[b], rf->cent[b]); + } + + // uncommented; this isnt satisfying, but i leave it in the code for now (ton) + // if(vlr->mat->translucency!=0.0) rf->flag |= RAD_TWOSIDED; + + radface=RE_vlakren_get_radface(obr, vlr, 1); + *radface= rf++; + } + } + } + RG.size[0]= (RG.max[0]- RG.min[0]); + RG.size[1]= (RG.max[1]- RG.min[1]); + RG.size[2]= (RG.max[2]- RG.min[2]); + RG.maxsize= MAX3(RG.size[0],RG.size[1],RG.size[2]); + + /* formfactor array */ + if(RG.formfactors) MEM_freeN(RG.formfactors); + if(RG.totelem) + RG.formfactors= MEM_mallocN(sizeof(float)*RG.totelem, "formfactors"); + else + RG.formfactors= NULL; + +} + +static void vecaddfac(float *vec, float *v1, float *v2, float fac) +{ + vec[0]= v1[0] + fac*v2[0]; + vec[1]= v1[1] + fac*v2[1]; + vec[2]= v1[2] + fac*v2[2]; + +} + +/* unused now, doesnt work..., find it in cvs of nov 2005 or older */ +/* static void filter_rad_values(void) */ + + +static void make_vertex_rad_values(Render *re) +{ + ObjectRen *obr; + VertRen *v1=NULL; + VlakRen *vlr=NULL; + RadFace *rf, **radface; + float *col; + int a; + + RG.igamma= 1.0/RG.gamma; + RG.radfactor= RG.radfac*pow(64*64, RG.igamma)/128.0; /* compatible with radio-tool */ + + /* accumulate vertexcolors */ + for(obr=re->objecttable.first; obr; obr=obr->next) { + for(a=0; a<obr->totvlak; a++) { + if((a & 255)==0) vlr= obr->vlaknodes[a>>8].vlak; else vlr++; + + if((radface=RE_vlakren_get_radface(obr, vlr, 0)) && *radface) { + rf= *radface; + + /* apply correction */ + rf->totrad[0]= RG.radfactor*pow( rf->totrad[0], RG.igamma); + rf->totrad[1]= RG.radfactor*pow( rf->totrad[1], RG.igamma); + rf->totrad[2]= RG.radfactor*pow( rf->totrad[2], RG.igamma); + + /* correct rf->rad values for color */ + if(vlr->mat->r > 0.0) rf->totrad[0]/= vlr->mat->r; + if(vlr->mat->g > 0.0) rf->totrad[1]/= vlr->mat->g; + if(vlr->mat->b > 0.0) rf->totrad[2]/= vlr->mat->b; + + col= RE_vertren_get_rad(obr, vlr->v1, 1); + vecaddfac(col, col, rf->totrad, rf->area); + col[3]+= rf->area; + + col= RE_vertren_get_rad(obr, vlr->v2, 1); + vecaddfac(col, col, rf->totrad, rf->area); + col[3]+= rf->area; + + col= RE_vertren_get_rad(obr, vlr->v3, 1); + vecaddfac(col, col, rf->totrad, rf->area); + col[3]+= rf->area; + + if(vlr->v4) { + col= RE_vertren_get_rad(obr, vlr->v4, 1); + vecaddfac(col, col, rf->totrad, rf->area); + col[3]+= rf->area; + } + } + } + + /* make vertex colors */ + for(a=0; a<obr->totvert; a++) { + if((a & 255)==0) v1= RE_findOrAddVert(obr, a); else v1++; + + col= RE_vertren_get_rad(obr, v1, 0); + if(col && col[3]>0.0) { + col[0]/= col[3]; + col[1]/= col[3]; + col[2]/= col[3]; + } + } + } +} + +/* main call, extern */ +void do_radio_render(Render *re) +{ + if(re->scene->radio==NULL) add_radio(re->scene); + freeAllRad(re->scene); /* just in case radio-tool is still used */ + + set_radglobal(re->scene); /* init the RG struct */ + RG.re= re; /* only used by hemizbuf(), prevents polluting radio code all over */ + + initradfaces(re); /* add radface structs to render faces */ + if(RG.totenergy>0.0) { + + initradiosity(); /* LUT's */ + inithemiwindows(); /* views, need RG.maxsize for clipping */ + + progressiverad_rr(re); /* main radio loop */ + + make_vertex_rad_values(re); /* convert face energy to vertex ones */ + + } + + freeAllRad(re->scene); /* luts, hemis, sets vars at zero */ +} + +/* free call, after rendering, extern */ +void end_radio_render(void) +{ + if(radfaces) MEM_freeN(radfaces); + radfaces= NULL; +} + diff --git a/source/blender/render/extern/include/RE_render_ext.h b/source/blender/render/extern/include/RE_render_ext.h index 15b59f2c8cc..20eea0c98bd 100644 --- a/source/blender/render/extern/include/RE_render_ext.h +++ b/source/blender/render/extern/include/RE_render_ext.h @@ -47,8 +47,7 @@ struct Render; struct MTex; struct ImBuf; -// RADIO REMOVED, Maybe this will be useful later -//void RE_zbufferall_radio(struct RadView *vw, struct RNode **rg_elem, int rg_totelem, struct Render *re); +void RE_zbufferall_radio(struct RadView *vw, struct RNode **rg_elem, int rg_totelem, struct Render *re); /* particle.c, effect.c, editmesh_modes.c and brush.c, returns 1 if rgb, 0 otherwise */ int externtex(struct MTex *mtex, float *vec, float *tin, float *tr, float *tg, float *tb, float *ta); diff --git a/source/blender/render/intern/source/convertblender.c b/source/blender/render/intern/source/convertblender.c index a00cd2211fc..98e5819c0d3 100644 --- a/source/blender/render/intern/source/convertblender.c +++ b/source/blender/render/intern/source/convertblender.c @@ -104,6 +104,7 @@ #include "rendercore.h" #include "renderdatabase.h" #include "renderpipeline.h" +#include "radio.h" #include "shadbuf.h" #include "shading.h" #include "strand.h" @@ -1885,9 +1886,6 @@ static int render_new_particle_system(Render *re, ObjectRen *obr, ParticleSystem if(psys_get_particle_state(re->scene,ob,psys,a,&state,0)==0) continue; - if(psys->parent) - Mat4MulVecfl(psys->parent->obmat, state.co); - VECCOPY(loc,state.co); if(part->ren_as!=PART_DRAW_BB) MTC_Mat4MulVecfl(re->viewmat,loc); @@ -4310,9 +4308,8 @@ void RE_Database_Free(Render *re) } free_mesh_orco_hash(re); -#if 0 /* radio can be redone better */ + end_radio_render(); -#endif end_render_materials(); end_render_textures(); @@ -4739,11 +4736,10 @@ void RE_Database_FromScene(Render *re, Scene *scene, int use_camera_view) /* yafray: 'direct' radiosity, environment maps and raytree init not needed for yafray render */ /* although radio mode could be useful at some point, later */ if (re->r.renderer==R_INTERN) { -#if 0 /* RADIO was removed */ /* RADIO (uses no R anymore) */ if(!re->test_break(re->tbh)) if(re->r.mode & R_RADIO) do_radio_render(re); -#endif + /* raytree */ if(!re->test_break(re->tbh)) { if(re->r.mode & R_RAYTRACE) { diff --git a/source/blender/render/intern/source/pipeline.c b/source/blender/render/intern/source/pipeline.c index ccc793e4235..07560edb76b 100644 --- a/source/blender/render/intern/source/pipeline.c +++ b/source/blender/render/intern/source/pipeline.c @@ -46,7 +46,6 @@ #include "BKE_object.h" #include "BKE_scene.h" #include "BKE_writeavi.h" /* <------ should be replaced once with generic movie module */ -#include "BKE_pointcache.h" #include "MEM_guardedalloc.h" @@ -62,6 +61,7 @@ #include "intern/openexr/openexr_multi.h" #include "RE_pipeline.h" +#include "radio.h" /* internal */ #include "render_types.h" @@ -2413,21 +2413,6 @@ static int is_rendering_allowed(Render *re) return 1; } -static void update_physics_cache(Render *re, Scene *scene) -{ - PTCacheBaker baker; - - baker.scene = scene; - baker.pid = NULL; - baker.bake = 0; - baker.render = 1; - baker.quick_step = 1; - baker.break_test = re->test_break; - baker.break_data = re->tbh; - baker.progressbar = NULL; - - BKE_ptcache_make_cache(&baker); -} /* evaluating scene options for general Blender render */ static int render_initialize_from_scene(Render *re, Scene *scene, int anim) { @@ -2465,9 +2450,6 @@ static int render_initialize_from_scene(Render *re, Scene *scene, int anim) /* check all scenes involved */ tag_scenes_for_render(re); - - /* make sure dynamics are up to date */ - update_physics_cache(re, scene); if(scene->r.scemode & R_SINGLE_LAYER) push_render_result(re); diff --git a/source/blender/render/intern/source/zbuf.c b/source/blender/render/intern/source/zbuf.c index 21c3977fc0b..b68cecce7bd 100644 --- a/source/blender/render/intern/source/zbuf.c +++ b/source/blender/render/intern/source/zbuf.c @@ -49,12 +49,14 @@ #include "DNA_mesh_types.h" #include "DNA_node_types.h" #include "DNA_meshdata_types.h" -#include "DNA_material_types.h" #include "BKE_global.h" #include "BKE_material.h" #include "BKE_utildefines.h" +#include "radio_types.h" +#include "radio.h" /* needs RG, some root data for radiosity */ + #include "RE_render_ext.h" /* local includes */ @@ -2299,6 +2301,110 @@ static int hashlist_projectvert(float *v1, float winmat[][4], float *hoco) return buck->clip; } +/* used for booth radio 'tool' as during render */ +void RE_zbufferall_radio(struct RadView *vw, RNode **rg_elem, int rg_totelem, Render *re) +{ + ZSpan zspan; + float hoco[4][4], winmat[4][4]; + int a, zvlnr; + int c1, c2, c3, c4= 0; + + if(rg_totelem==0) return; + + hashlist_projectvert(NULL, winmat, NULL); + + /* needed for projectvert */ + MTC_Mat4MulMat4(winmat, vw->viewmat, vw->winmat); + + /* 1.0f for clipping in clippyra()... bad stuff actually */ + zbuf_alloc_span(&zspan, vw->rectx, vw->recty, 1.0f); + zspan.zmulx= ((float)vw->rectx)/2.0; + zspan.zmuly= ((float)vw->recty)/2.0; + zspan.zofsx= -0.5f; + zspan.zofsy= -0.5f; + + /* the buffers */ + zspan.rectz= (int *)vw->rectz; + zspan.rectp= (int *)vw->rect; + zspan.recto= MEM_callocN(sizeof(int)*vw->rectx*vw->recty, "radiorecto"); + fillrect(zspan.rectz, vw->rectx, vw->recty, 0x7FFFFFFF); + fillrect(zspan.rectp, vw->rectx, vw->recty, 0xFFFFFF); + + /* filling methods */ + zspan.zbuffunc= zbuffillGL4; + + if(rg_elem) { /* radio tool */ + RNode **re, *rn; + + re= rg_elem; + re+= (rg_totelem-1); + for(a= rg_totelem-1; a>=0; a--, re--) { + rn= *re; + if( (rn->f & RAD_SHOOT)==0 ) { /* no shootelement */ + + if( rn->f & RAD_TWOSIDED) zvlnr= a; + else if( rn->f & RAD_BACKFACE) zvlnr= 0xFFFFFF; + else zvlnr= a; + + c1= hashlist_projectvert(rn->v1, winmat, hoco[0]); + c2= hashlist_projectvert(rn->v2, winmat, hoco[1]); + c3= hashlist_projectvert(rn->v3, winmat, hoco[2]); + + if(rn->v4) { + c4= hashlist_projectvert(rn->v4, winmat, hoco[3]); + } + + if(rn->v4) + zbufclip4(&zspan, 0, zvlnr, hoco[0], hoco[1], hoco[2], hoco[3], c1, c2, c3, c4); + else + zbufclip(&zspan, 0, zvlnr, hoco[0], hoco[1], hoco[2], c1, c2, c3); + } + } + } + else { /* radio render */ + ObjectRen *obr; + VlakRen *vlr=NULL; + RadFace **radface, *rf; + int totface=0; + + /* note: radio render doesn't support duplis */ + for(obr=re->objecttable.first; obr; obr=obr->next) { + hashlist_projectvert(NULL, NULL, NULL); /* clear hashlist */ + + for(a=0; a<obr->totvlak; a++) { + if((a & 255)==0) vlr= obr->vlaknodes[a>>8].vlak; else vlr++; + + if((radface=RE_vlakren_get_radface(obr, vlr, 0)) && *radface) { + rf= *radface; + if( (rf->flag & RAD_SHOOT)==0 ) { /* no shootelement */ + + if( rf->flag & RAD_TWOSIDED) zvlnr= totface; + else if( rf->flag & RAD_BACKFACE) zvlnr= 0xFFFFFF; /* receives no energy, but is zbuffered */ + else zvlnr= totface; + + c1= hashlist_projectvert(vlr->v1->co, winmat, hoco[0]); + c2= hashlist_projectvert(vlr->v2->co, winmat, hoco[1]); + c3= hashlist_projectvert(vlr->v3->co, winmat, hoco[2]); + + if(vlr->v4) { + c4= hashlist_projectvert(vlr->v4->co, winmat, hoco[3]); + } + + if(vlr->v4) + zbufclip4(&zspan, 0, zvlnr, hoco[0], hoco[1], hoco[2], hoco[3], c1, c2, c3, c4); + else + zbufclip(&zspan, 0, zvlnr, hoco[0], hoco[1], hoco[2], c1, c2, c3); + } + totface++; + } + } + } + } + + MEM_freeN(zspan.recto); + zbuf_free_span(&zspan); +} + void zbuffer_shadow(Render *re, float winmat[][4], LampRen *lar, int *rectz, int size, float jitx, float jity) { ZbufProjectCache cache[ZBUF_PROJECT_CACHE_SIZE]; diff --git a/source/blender/windowmanager/WM_api.h b/source/blender/windowmanager/WM_api.h index ffeb342df77..7acb2921bec 100644 --- a/source/blender/windowmanager/WM_api.h +++ b/source/blender/windowmanager/WM_api.h @@ -79,7 +79,7 @@ void WM_keymap_tweak (ListBase *lb, short type, short val, int modifier, short ListBase *WM_keymap_listbase (struct wmWindowManager *wm, const char *nameid, int spaceid, int regionid); -const char *WM_key_event_string(short type); +char *WM_key_event_string(short type); char *WM_key_event_operator_string(const struct bContext *C, const char *opname, int opcontext, struct IDProperty *properties, char *str, int len); /* handlers */ @@ -129,8 +129,6 @@ int WM_operator_redo_popup (struct bContext *C, struct wmOperator *op); /* operator api */ void WM_operator_free (struct wmOperator *op); -void WM_operator_stack_clear(struct bContext *C); - wmOperatorType *WM_operatortype_find(const char *idname); wmOperatorType *WM_operatortype_first(void); void WM_operatortype_append (void (*opfunc)(wmOperatorType*)); @@ -214,8 +212,8 @@ void WM_jobs_stop(struct wmWindowManager *wm, void *owner); void WM_jobs_stop_all(struct wmWindowManager *wm); /* clipboard */ -char *WM_clipboard_text_get(int selection); -void WM_clipboard_text_set(char *buf, int selection); +char *WM_clipboard_text_get(int selection); +void WM_clipboard_text_set(char *buf, int selection); #endif /* WM_API_H */ diff --git a/source/blender/windowmanager/WM_types.h b/source/blender/windowmanager/WM_types.h index 9b987cdfa51..739cfbcc1ac 100644 --- a/source/blender/windowmanager/WM_types.h +++ b/source/blender/windowmanager/WM_types.h @@ -58,6 +58,37 @@ enum { WM_OP_EXEC_SCREEN }; +/* ************** wmEvent ************************ */ + +/* each event should have full modifier state */ +/* event comes from eventmanager and from keymap */ +typedef struct wmEvent { + struct wmEvent *next, *prev; + + short type; /* event code itself (short, is also in keymap) */ + short val; /* press, release, scrollvalue */ + short x, y; /* mouse pointer position, screen coord */ + short mval[2]; /* region mouse position, name convention pre 2.5 :) */ + short prevx, prevy; /* previous mouse pointer position */ + short unicode; /* future, ghost? */ + char ascii; /* from ghost */ + char pad; + + /* modifier states */ + short shift, ctrl, alt, oskey; /* oskey is apple or windowskey, value denotes order of pressed */ + short keymodifier; /* rawkey modifier */ + + /* keymap item, set by handler (weak?) */ + const char *keymap_idname; + + /* custom data */ + short custom; /* custom data type, stylus, 6dof, see wm_event_types.h */ + void *customdata; /* ascii, unicode, mouse coords, angles, vectors, dragdrop info */ + short customdatafree; + +} wmEvent; + + /* ************** wmKeyMap ************************ */ /* modifier */ diff --git a/source/blender/windowmanager/intern/Makefile b/source/blender/windowmanager/intern/Makefile index 8f0f47c52d0..80ae58f9398 100644 --- a/source/blender/windowmanager/intern/Makefile +++ b/source/blender/windowmanager/intern/Makefile @@ -1,5 +1,5 @@ # -# $Id$ +# $Id: Makefile 11904 2007-08-31 16:16:33Z sirdude $ # # ***** BEGIN GPL LICENSE BLOCK ***** # diff --git a/source/blender/windowmanager/intern/wm.c b/source/blender/windowmanager/intern/wm.c index 7dec14664ae..37fdc9fa2c5 100644 --- a/source/blender/windowmanager/intern/wm.c +++ b/source/blender/windowmanager/intern/wm.c @@ -95,18 +95,6 @@ void wm_operator_register(wmWindowManager *wm, wmOperator *op) } -void WM_operator_stack_clear(bContext *C) -{ - wmWindowManager *wm= CTX_wm_manager(C); - wmOperator *op; - - while((op= wm->operators.first)) { - BLI_remlink(&wm->operators, op); - WM_operator_free(op); - } - -} - /* ****************************************** */ void wm_check(bContext *C) diff --git a/source/blender/windowmanager/intern/wm_event_system.c b/source/blender/windowmanager/intern/wm_event_system.c index 286d1216f66..ea6a65859e5 100644 --- a/source/blender/windowmanager/intern/wm_event_system.c +++ b/source/blender/windowmanager/intern/wm_event_system.c @@ -49,7 +49,6 @@ #include "BKE_report.h" #include "BKE_scene.h" #include "BKE_utildefines.h" -#include "BKE_pointcache.h" #include "ED_fileselect.h" #include "ED_screen.h" @@ -235,8 +234,6 @@ void wm_event_do_notifiers(bContext *C) for(base= scene->base.first; base; base= base->next) { object_handle_update(scene, base->object); } - - BKE_ptcache_quick_cache_all(scene); } } CTX_wm_window_set(C, NULL); diff --git a/source/blender/windowmanager/intern/wm_files.c b/source/blender/windowmanager/intern/wm_files.c index 861080f30ba..d13d8ec6ccc 100644 --- a/source/blender/windowmanager/intern/wm_files.c +++ b/source/blender/windowmanager/intern/wm_files.c @@ -294,6 +294,8 @@ int WM_read_homefile(bContext *C, wmOperator *op) G.relbase_valid = 0; if (!from_memory) { BLI_make_file_string(G.sce, tstr, home, ".B25.blend"); + if(!BLI_exists(tstr)) + BLI_make_file_string(G.sce, tstr, home, ".B.blend"); } strcpy(scestr, G.sce); /* temporary store */ diff --git a/source/blender/windowmanager/intern/wm_init_exit.c b/source/blender/windowmanager/intern/wm_init_exit.c index 0bc35ffa9b2..adbc43e439d 100644 --- a/source/blender/windowmanager/intern/wm_init_exit.c +++ b/source/blender/windowmanager/intern/wm_init_exit.c @@ -58,6 +58,8 @@ #include "RE_pipeline.h" /* RE_ free stuff */ +#include "radio.h" + #ifndef DISABLE_PYTHON #include "BPY_extern.h" #endif @@ -194,6 +196,9 @@ void WM_exit(bContext *C) // BIF_freeRetarget(); BIF_freeTemplates(C); BIF_freeSketch(C); + + /* Context should still working here. but radio tool needs cleaning... */ + freeAllRad(CTX_data_scene(C)); free_ttfont(); /* bke_font.h */ diff --git a/source/blender/windowmanager/intern/wm_keymap.c b/source/blender/windowmanager/intern/wm_keymap.c index b914e63788d..7528321c7c5 100644 --- a/source/blender/windowmanager/intern/wm_keymap.c +++ b/source/blender/windowmanager/intern/wm_keymap.c @@ -44,7 +44,6 @@ #include "RNA_access.h" #include "RNA_types.h" -#include "RNA_enum_types.h" #include "WM_api.h" #include "WM_types.h" @@ -154,11 +153,315 @@ ListBase *WM_keymap_listbase(wmWindowManager *wm, const char *nameid, int spacei /* ***************** get string from key events **************** */ -const char *WM_key_event_string(short type) +char *WM_key_event_string(short type) { - const char *name= NULL; - if(RNA_enum_name(event_type_items, (int)type, &name)) - return name; + /* not returned: CAPSLOCKKEY, UNKNOWNKEY, COMMANDKEY, GRLESSKEY */ + + switch(type) { + case AKEY: + return "A"; + break; + case BKEY: + return "B"; + break; + case CKEY: + return "C"; + break; + case DKEY: + return "D"; + break; + case EKEY: + return "E"; + break; + case FKEY: + return "F"; + break; + case GKEY: + return "G"; + break; + case HKEY: + return "H"; + break; + case IKEY: + return "I"; + break; + case JKEY: + return "J"; + break; + case KKEY: + return "K"; + break; + case LKEY: + return "L"; + break; + case MKEY: + return "M"; + break; + case NKEY: + return "N"; + break; + case OKEY: + return "O"; + break; + case PKEY: + return "P"; + break; + case QKEY: + return "Q"; + break; + case RKEY: + return "R"; + break; + case SKEY: + return "S"; + break; + case TKEY: + return "T"; + break; + case UKEY: + return "U"; + break; + case VKEY: + return "V"; + break; + case WKEY: + return "W"; + break; + case XKEY: + return "X"; + break; + case YKEY: + return "Y"; + break; + case ZKEY: + return "Z"; + break; + + case ZEROKEY: + return "Zero"; + break; + case ONEKEY: + return "One"; + break; + case TWOKEY: + return "Two"; + break; + case THREEKEY: + return "Three"; + break; + case FOURKEY: + return "Four"; + break; + case FIVEKEY: + return "Five"; + break; + case SIXKEY: + return "Six"; + break; + case SEVENKEY: + return "Seven"; + break; + case EIGHTKEY: + return "Eight"; + break; + case NINEKEY: + return "Nine"; + break; + + case LEFTCTRLKEY: + return "Leftctrl"; + break; + case LEFTALTKEY: + return "Leftalt"; + break; + case RIGHTALTKEY: + return "Rightalt"; + break; + case RIGHTCTRLKEY: + return "Rightctrl"; + break; + case RIGHTSHIFTKEY: + return "Rightshift"; + break; + case LEFTSHIFTKEY: + return "Leftshift"; + break; + + case ESCKEY: + return "Esc"; + break; + case TABKEY: + return "Tab"; + break; + case RETKEY: + return "Ret"; + break; + case SPACEKEY: + return "Space"; + break; + case LINEFEEDKEY: + return "Linefeed"; + break; + case BACKSPACEKEY: + return "Backspace"; + break; + case DELKEY: + return "Del"; + break; + case SEMICOLONKEY: + return "Semicolon"; + break; + case PERIODKEY: + return "Period"; + break; + case COMMAKEY: + return "Comma"; + break; + case QUOTEKEY: + return "Quote"; + break; + case ACCENTGRAVEKEY: + return "Accentgrave"; + break; + case MINUSKEY: + return "Minus"; + break; + case SLASHKEY: + return "Slash"; + break; + case BACKSLASHKEY: + return "Backslash"; + break; + case EQUALKEY: + return "Equal"; + break; + case LEFTBRACKETKEY: + return "Leftbracket"; + break; + case RIGHTBRACKETKEY: + return "Rightbracket"; + break; + + case LEFTARROWKEY: + return "Leftarrow"; + break; + case DOWNARROWKEY: + return "Downarrow"; + break; + case RIGHTARROWKEY: + return "Rightarrow"; + break; + case UPARROWKEY: + return "Uparrow"; + break; + + case PAD2: + return "Numpad 2"; + break; + case PAD4: + return "Numpad 4"; + break; + case PAD6: + return "Numpad 6"; + break; + case PAD8: + return "Numpad 8"; + break; + case PAD1: + return "Numpad 1"; + break; + case PAD3: + return "Numpad 3"; + break; + case PAD5: + return "Numpad 5"; + break; + case PAD7: + return "Numpad 7"; + break; + case PAD9: + return "Numpad 9"; + break; + + case PADPERIOD: + return "Numpad ."; + break; + case PADSLASHKEY: + return "Numpad /"; + break; + case PADASTERKEY: + return "Numpad *"; + break; + + case PAD0: + return "Numpad 0"; + break; + case PADMINUS: + return "Numpad -"; + break; + case PADENTER: + return "Numpad Enter"; + break; + case PADPLUSKEY: + return "Numpad +"; + break; + + case F1KEY: + return "F1"; + break; + case F2KEY: + return "F2"; + break; + case F3KEY: + return "F3"; + break; + case F4KEY: + return "F4"; + break; + case F5KEY: + return "F5"; + break; + case F6KEY: + return "F6"; + break; + case F7KEY: + return "F7"; + break; + case F8KEY: + return "F8"; + break; + case F9KEY: + return "F9"; + break; + case F10KEY: + return "F10"; + break; + case F11KEY: + return "F11"; + break; + case F12KEY: + return "F12"; + break; + + case PAUSEKEY: + return "Pause"; + break; + case INSERTKEY: + return "Insert"; + break; + case HOMEKEY: + return "Home"; + break; + case PAGEUPKEY: + return "Pageup"; + break; + case PAGEDOWNKEY: + return "Pagedown"; + break; + case ENDKEY: + return "End"; + break; + } return ""; } diff --git a/source/blender/windowmanager/intern/wm_operators.c b/source/blender/windowmanager/intern/wm_operators.c index 7f9a2153dc3..46e9df10adc 100644 --- a/source/blender/windowmanager/intern/wm_operators.c +++ b/source/blender/windowmanager/intern/wm_operators.c @@ -145,6 +145,7 @@ char *WM_operator_pystring(wmOperator *op) const char *arg_name= NULL; PropertyRNA *prop, *iterprop; + CollectionPropertyIterator iter; /* for building the string */ DynStr *dynstr= BLI_dynstr_new(); @@ -154,9 +155,10 @@ char *WM_operator_pystring(wmOperator *op) BLI_dynstr_appendf(dynstr, "%s(", op->idname); iterprop= RNA_struct_iterator_property(op->ptr->type); + RNA_property_collection_begin(op->ptr, iterprop, &iter); - RNA_PROP_BEGIN(op->ptr, propptr, iterprop) { - prop= propptr.data; + for(; iter.valid; RNA_property_collection_next(&iter)) { + prop= iter.ptr.data; arg_name= RNA_property_identifier(prop); if (strcmp(arg_name, "rna_type")==0) continue; @@ -168,7 +170,8 @@ char *WM_operator_pystring(wmOperator *op) MEM_freeN(buf); first_iter = 0; } - RNA_PROP_END; + + RNA_property_collection_end(&iter); BLI_dynstr_append(dynstr, ")"); @@ -288,7 +291,7 @@ static uiBlock *wm_block_create_redo(bContext *C, ARegion *ar, void *arg_op) RNA_pointer_create(&wm->id, op->type->srna, op->properties, &ptr); layout= uiBlockLayout(block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, 0, 0, 300, 20, style); - uiDefAutoButsRNA(C, layout, &ptr, 2); + uiDefAutoButsRNA(C, layout, &ptr); uiPopupBoundsBlock(block, 4.0f, 0, 0); uiEndBlock(C, block); @@ -330,7 +333,7 @@ static uiBlock *wm_block_create_menu(bContext *C, ARegion *ar, void *arg_op) uiBlockSetFlag(block, UI_BLOCK_KEEP_OPEN|UI_BLOCK_RET_1); layout= uiBlockLayout(block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, 0, 0, 300, 20, style); - uiDefAutoButsRNA(C, layout, op->ptr, 2); + uiDefAutoButsRNA(C, layout, op->ptr); uiPopupBoundsBlock(block, 4.0f, 0, 0); uiEndBlock(C, block); @@ -399,7 +402,7 @@ static void operator_search_cb(const struct bContext *C, void *arg, char *str, u name[len]= '|'; } - if(0==uiSearchItemAdd(items, name, ot, 0)) + if(0==uiSearchItemAdd(items, name, ot)) break; } } @@ -418,7 +421,7 @@ static uiBlock *wm_block_search_menu(bContext *C, ARegion *ar, void *arg_op) uiBlockSetFlag(block, UI_BLOCK_LOOP|UI_BLOCK_RET_1); but= uiDefSearchBut(block, search, 0, ICON_VIEWZOOM, 256, 10, 10, 180, 19, ""); - uiButSetSearchFunc(but, operator_search_cb, NULL, operator_call_cb, NULL); + uiButSetSearchFunc(but, operator_search_cb, NULL, operator_call_cb); /* fake button, it holds space for search items */ uiDefBut(block, LABEL, 0, "", 10, 10 - uiSearchBoxhHeight(), 180, uiSearchBoxhHeight(), NULL, 0, 0, 0, 0, NULL); @@ -500,7 +503,7 @@ static void WM_OT_read_homefile(wmOperatorType *ot) static int recentfile_exec(bContext *C, wmOperator *op) { - int event= RNA_int_get(op->ptr, "nr"); + int event= RNA_enum_get(op->ptr, "nr"); // XXX wm in context is not set correctly after WM_read_file -> crash // do it before for now, but is this correct with multiple windows? @@ -554,7 +557,7 @@ static void WM_OT_open_recentfile(wmOperatorType *ot) ot->exec= recentfile_exec; ot->poll= WM_operator_winactive; - RNA_def_property(ot->srna, "nr", PROP_INT, PROP_UNSIGNED); + RNA_def_property(ot->srna, "nr", PROP_ENUM, PROP_NONE); } /* ********* main file *********** */ diff --git a/source/blender/windowmanager/intern/wm_subwindow.c b/source/blender/windowmanager/intern/wm_subwindow.c index 835fdca52fe..9bd55e1c5a7 100644 --- a/source/blender/windowmanager/intern/wm_subwindow.c +++ b/source/blender/windowmanager/intern/wm_subwindow.c @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: mywindow.c 9584 2007-01-03 13:45:03Z ton $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/windowmanager/wm_cursors.h b/source/blender/windowmanager/wm_cursors.h index 3d1b49983ed..1a1a0d0b71d 100644 --- a/source/blender/windowmanager/wm_cursors.h +++ b/source/blender/windowmanager/wm_cursors.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: BIF_cursors.h 7739 2006-06-15 14:22:59Z broken $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/blender/windowmanager/wm_subwindow.h b/source/blender/windowmanager/wm_subwindow.h index c0c492018ff..dfba9c27f17 100644 --- a/source/blender/windowmanager/wm_subwindow.h +++ b/source/blender/windowmanager/wm_subwindow.h @@ -1,5 +1,5 @@ /** - * $Id$ + * $Id: wm_subwindow.h 21247 2009-06-29 21:50:53Z jaguarandi $ * * ***** BEGIN GPL LICENSE BLOCK ***** * diff --git a/source/creator/CMakeLists.txt b/source/creator/CMakeLists.txt index ade5a2a64a8..4701eba810f 100644 --- a/source/creator/CMakeLists.txt +++ b/source/creator/CMakeLists.txt @@ -198,7 +198,7 @@ ADD_DEPENDENCIES(blender makesdna) FILE(READ ${CMAKE_BINARY_DIR}/cmake_blender_libs.txt BLENDER_LINK_LIBS) -SET(BLENDER_LINK_LIBS bf_nodes ${BLENDER_LINK_LIBS} bf_windowmanager bf_editors blender_render) +SET(BLENDER_LINK_LIBS bf_nodes ${BLENDER_LINK_LIBS} bf_windowmanager bf_editors blender_render blender_radiosity) IF(WITH_ELBEEM) SET(BLENDER_LINK_LIBS ${BLENDER_LINK_LIBS} bf_elbeem) @@ -218,6 +218,7 @@ IF(UNIX) bf_ghost bf_string blender_render + blender_radiosity blender_ONL bf_python bf_gen_python @@ -237,6 +238,7 @@ IF(UNIX) bf_kernel bf_decimation bf_elbeem + bf_yafray bf_IK bf_memutil bf_guardedalloc @@ -262,7 +264,10 @@ IF(UNIX) bf_ngnetwork extern_bullet bf_loopbacknetwork + bf_sumo bf_common + extern_solid + extern_qhull bf_moto bf_python bf_gen_python diff --git a/source/gameengine/BlenderRoutines/BL_KetsjiEmbedStart.cpp b/source/gameengine/BlenderRoutines/BL_KetsjiEmbedStart.cpp index fb222b419c3..44678cb73eb 100644 --- a/source/gameengine/BlenderRoutines/BL_KetsjiEmbedStart.cpp +++ b/source/gameengine/BlenderRoutines/BL_KetsjiEmbedStart.cpp @@ -65,14 +65,6 @@ #include "SYS_System.h" -#include "GPU_extensions.h" -#include "Value.h" - - - -#ifdef __cplusplus -extern "C" { -#endif /***/ #include "DNA_view3d_types.h" #include "DNA_screen_types.h" @@ -85,13 +77,21 @@ extern "C" { //XXX #include "BIF_scrarea.h" #include "BKE_main.h" +//#include "BKE_context.h" #include "BLI_blenlib.h" #include "BLO_readfile.h" #include "DNA_scene_types.h" /***/ +#include "GPU_extensions.h" +#include "Value.h" + + + +#ifdef __cplusplus +extern "C" { +#endif //XXX #include "BSE_headerbuttons.h" -#include "BKE_context.h" #include "../../blender/windowmanager/WM_types.h" #include "../../blender/windowmanager/wm_window.h" #include "../../blender/windowmanager/wm_event_system.h" @@ -118,10 +118,19 @@ static BlendFileData *load_game_data(char *filename) return bfd; } + +/* screw it, BKE_context.h is complaining! */ +extern "C" struct wmWindow *CTX_wm_window(const bContext *C); +extern "C" struct ScrArea *CTX_wm_area(const bContext *C); +extern "C" struct ARegion *CTX_wm_region(const bContext *C); +extern "C" struct Scene *CTX_data_scene(const bContext *C); +extern "C" struct Main *CTX_data_main(const bContext *C); + extern "C" void StartKetsjiShell(struct bContext *C, int always_use_expand_framing) { /* context values */ struct wmWindow *win= CTX_wm_window(C); + struct ScrArea *area= CTX_wm_area(C); // curarea struct ARegion *ar= CTX_wm_region(C); struct Scene *scene= CTX_data_scene(C); struct Main* maggie1= CTX_data_main(C); @@ -150,8 +159,8 @@ extern "C" void StartKetsjiShell(struct bContext *C, int always_use_expand_frami do { - View3D *v3d= CTX_wm_view3d(C); - RegionView3D *rv3d= CTX_wm_region_view3d(C); + View3D *v3d= (View3D*) area->spacedata.first; + RegionView3D *rv3d= (RegionView3D*) ar->regiondata; // get some preferences SYS_SystemHandle syshandle = SYS_GetSystem(); @@ -230,12 +239,13 @@ extern "C" void StartKetsjiShell(struct bContext *C, int always_use_expand_frami scene->camera= v3d->camera; } + // some blender stuff MT_CmMatrix4x4 projmat; MT_CmMatrix4x4 viewmat; float camzoom; int i; - + for (i = 0; i < 16; i++) { float *viewmat_linear= (float*) rv3d->viewmat; @@ -247,7 +257,7 @@ extern "C" void StartKetsjiShell(struct bContext *C, int always_use_expand_frami projmat.setElem(i, projmat_linear[i]); } - if(rv3d->persp==V3D_CAMOB) { + if(v3d->persp==V3D_CAMOB) { camzoom = (1.41421 + (rv3d->camzoom / 50.0)); camzoom *= camzoom; } @@ -338,10 +348,10 @@ extern "C" void StartKetsjiShell(struct bContext *C, int always_use_expand_frami if (exitrequested != KX_EXIT_REQUEST_QUIT_GAME) { - if (rv3d->persp != V3D_CAMOB) + if (v3d->persp != V3D_CAMOB) { ketsjiengine->EnableCameraOverride(startscenename); - ketsjiengine->SetCameraOverrideUseOrtho((rv3d->persp == V3D_ORTHO)); + ketsjiengine->SetCameraOverrideUseOrtho((v3d->persp == V3D_ORTHO)); ketsjiengine->SetCameraOverrideProjectionMatrix(projmat); ketsjiengine->SetCameraOverrideViewMatrix(viewmat); ketsjiengine->SetCameraOverrideClipping(v3d->near, v3d->far); @@ -577,6 +587,7 @@ extern "C" void StartKetsjiShell(struct bContext *C, int always_use_expand_frami } extern "C" void StartKetsjiShellSimulation(struct wmWindow *win, + struct ScrArea *area, struct ARegion *ar, char* scenename, struct Main* maggie, diff --git a/source/gameengine/BlenderRoutines/CMakeLists.txt b/source/gameengine/BlenderRoutines/CMakeLists.txt index 2874a0273cc..3b690a21584 100644 --- a/source/gameengine/BlenderRoutines/CMakeLists.txt +++ b/source/gameengine/BlenderRoutines/CMakeLists.txt @@ -19,8 +19,7 @@ SET(INC ../../../source/blender/windowmanager ../../../source/blender ../../../source/blender/include - ../../../source/blender/makesdna - ../../../source/blender/makesrna + ../../../source/blender/makesdna ../../../source/gameengine/Rasterizer ../../../source/gameengine/GameLogic ../../../source/gameengine/Expressions diff --git a/source/gameengine/BlenderRoutines/KX_BlenderCanvas.cpp b/source/gameengine/BlenderRoutines/KX_BlenderCanvas.cpp index 360794ceb33..aa83d17a03a 100644 --- a/source/gameengine/BlenderRoutines/KX_BlenderCanvas.cpp +++ b/source/gameengine/BlenderRoutines/KX_BlenderCanvas.cpp @@ -28,13 +28,11 @@ #include "KX_BlenderCanvas.h" #include "DNA_screen_types.h" -#include "stdio.h" #ifdef HAVE_CONFIG_H #include <config.h> #endif - KX_BlenderCanvas::KX_BlenderCanvas(struct wmWindow *win, ARegion *ar) : m_win(win), m_ar(ar) diff --git a/source/gameengine/BlenderRoutines/Makefile b/source/gameengine/BlenderRoutines/Makefile index ffa99a0c1b2..f5486bae87b 100644 --- a/source/gameengine/BlenderRoutines/Makefile +++ b/source/gameengine/BlenderRoutines/Makefile @@ -36,6 +36,8 @@ include nan_compile.mk CCFLAGS += $(LEVEL_1_CPP_WARNINGS) CPPFLAGS += -I$(NAN_GLEW)/include +CPPFLAGS += -I$(NAN_SUMO)/include -I$(NAN_SOLID)/include +CPPFLAGS += -I$(NAN_SOLID) CPPFLAGS += -I$(NAN_STRING)/include CPPFLAGS += -I$(NAN_MOTO)/include CPPFLAGS += -I$(NAN_FUZZICS)/include @@ -54,7 +56,6 @@ CPPFLAGS += -I../../blender/render/extern/include CPPFLAGS += -I../../blender/blenloader CPPFLAGS += -I../../blender/blenfont CPPFLAGS += -I../../blender/gpu -CPPFLAGS += -I../../blender/makesrna CPPFLAGS += -I../Converter CPPFLAGS += -I../Expressions CPPFLAGS += -I../GameLogic @@ -66,6 +67,7 @@ CPPFLAGS += -I../../kernel/gen_system CPPFLAGS += -I../Network CPPFLAGS += -I../Network/LoopBackNetwork CPPFLAGS += -I../Physics/common +CPPFLAGS += -I../Physics/Sumo CPPFLAGS += -I. ifeq ($(OS),windows) diff --git a/source/gameengine/BlenderRoutines/SConscript b/source/gameengine/BlenderRoutines/SConscript index fc12f453d86..a0cc3af3611 100644 --- a/source/gameengine/BlenderRoutines/SConscript +++ b/source/gameengine/BlenderRoutines/SConscript @@ -11,8 +11,7 @@ incs += ' #intern/ghost/include' incs += ' #intern/moto/include #source/gameengine/Ketsji #source/blender/blenlib' incs += ' #source/blender/blenkernel #source/blender' incs += ' #source/blender/blenfont #source/blender/editors/include' -incs += ' #source/blender/makesdna #source/blender/makesrna' -incs += ' #source/gameengine/Rasterizer #source/gameengine/GameLogic' +incs += ' #source/blender/makesdna #source/gameengine/Rasterizer #source/gameengine/GameLogic' incs += ' #source/gameengine/Expressions #source/gameengine/Network' incs += ' #source/gameengine/SceneGraph #source/gameengine/Physics/common' incs += ' #source/gameengine/Physics/Bullet' @@ -21,6 +20,11 @@ incs += ' #intern/SoundSystem #source/blender/misc #source/blender/blenloader' incs += ' #extern/glew/include #source/blender/gpu' incs += ' #source/blender/windowmanager' +if env['WITH_BF_SOLID']: + incs += ' #source/gameengine/Physics/Sumo #source/gameengine/Physics/Sumo/Fuzzics/include' + incs += ' ' + env['BF_SOLID_INC'] + defs.append('USE_SUMO_SOLID') + if env['WITH_BF_FFMPEG']: defs.append('WITH_FFMPEG') diff --git a/source/gameengine/CMakeLists.txt b/source/gameengine/CMakeLists.txt index f546a31fb2e..fd05858710d 100644 --- a/source/gameengine/CMakeLists.txt +++ b/source/gameengine/CMakeLists.txt @@ -38,6 +38,7 @@ ADD_SUBDIRECTORY(Rasterizer) ADD_SUBDIRECTORY(Rasterizer/RAS_OpenGLRasterizer) ADD_SUBDIRECTORY(SceneGraph) ADD_SUBDIRECTORY(Physics/Bullet) +ADD_SUBDIRECTORY(Physics/Sumo) ADD_SUBDIRECTORY(VideoTexture) IF(WITH_PLAYER) diff --git a/source/gameengine/Converter/BL_ActionActuator.cpp b/source/gameengine/Converter/BL_ActionActuator.cpp index bed99a4f502..c0d28d28bda 100644 --- a/source/gameengine/Converter/BL_ActionActuator.cpp +++ b/source/gameengine/Converter/BL_ActionActuator.cpp @@ -446,7 +446,7 @@ PyObject* BL_ActionActuator::PyGetAction(PyObject* args, ShowDeprecationWarning("getAction()", "the action property"); if (m_action){ - return PyUnicode_FromString(m_action->id.name+2); + return PyString_FromString(m_action->id.name+2); } Py_RETURN_NONE; } @@ -796,7 +796,7 @@ PyObject* BL_ActionActuator::PySetFrameProperty(PyObject* args, } PyObject* BL_ActionActuator::PyGetChannel(PyObject* value) { - char *string= _PyUnicode_AsString(value); + char *string= PyString_AsString(value); if (!string) { PyErr_SetString(PyExc_TypeError, "expected a single string"); @@ -888,7 +888,7 @@ PyObject* BL_ActionActuator::PySetType(PyObject* args, PyObject* BL_ActionActuator::PyGetContinue() { ShowDeprecationWarning("getContinue()", "the continue property"); - return PyLong_FromSsize_t((long)(m_end_reset==0)); + return PyInt_FromLong((long)(m_end_reset==0)); } PyObject* BL_ActionActuator::PySetContinue(PyObject* value) { @@ -962,9 +962,9 @@ KX_PYMETHODDEF_DOC(BL_ActionActuator, setChannel, else { MT_Vector3 loc; MT_Vector3 size; - MT_Quaternion quat; + MT_Vector4 quat; - if (!PyVecTo(pyloc, loc) || !PyVecTo(pysize, size) || !PyQuatTo(pyquat, quat)) + if (!PyVecTo(pyloc, loc) || !PyVecTo(pysize, size) || !PyVecTo(pyquat, quat)) return NULL; // same as above @@ -977,7 +977,7 @@ KX_PYMETHODDEF_DOC(BL_ActionActuator, setChannel, // for some reason loc.setValue(pchan->loc) fails pchan->loc[0]= loc[0]; pchan->loc[1]= loc[1]; pchan->loc[2]= loc[2]; pchan->size[0]= size[0]; pchan->size[1]= size[1]; pchan->size[2]= size[2]; - pchan->quat[0]= quat[3]; pchan->quat[1]= quat[0]; pchan->quat[2]= quat[1]; pchan->quat[3]= quat[2]; /* notice xyzw -> wxyz is intentional */ + pchan->quat[0]= quat[0]; pchan->quat[1]= quat[1]; pchan->quat[2]= quat[2]; pchan->quat[3]= quat[3]; } pchan->flag |= POSE_ROT|POSE_LOC|POSE_SIZE; @@ -1005,15 +1005,19 @@ PyTypeObject BL_ActionActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject BL_ActionActuator::Parents[] = { + &BL_ActionActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef BL_ActionActuator::Methods[] = { @@ -1061,24 +1065,37 @@ PyAttributeDef BL_ActionActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* BL_ActionActuator::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IActuator); +} + +PyObject* BL_ActionActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int BL_ActionActuator::py_setattro(PyObject *attr, PyObject* value) { + py_setattro_up(SCA_IActuator); +} + + PyObject* BL_ActionActuator::pyattr_get_action(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { BL_ActionActuator* self= static_cast<BL_ActionActuator*>(self_v); - return PyUnicode_FromString(self->GetAction() ? self->GetAction()->id.name+2 : ""); + return PyString_FromString(self->GetAction() ? self->GetAction()->id.name+2 : ""); } int BL_ActionActuator::pyattr_set_action(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) { BL_ActionActuator* self= static_cast<BL_ActionActuator*>(self_v); - if (!PyUnicode_Check(value)) + if (!PyString_Check(value)) { PyErr_SetString(PyExc_ValueError, "actuator.action = val: Action Actuator, expected the string name of the action"); return PY_SET_ATTR_FAIL; } bAction *action= NULL; - STR_String val = _PyUnicode_AsString(value); + STR_String val = PyString_AsString(value); if (val != "") { diff --git a/source/gameengine/Converter/BL_ActionActuator.h b/source/gameengine/Converter/BL_ActionActuator.h index e328ce126ca..422b16bb3ec 100644 --- a/source/gameengine/Converter/BL_ActionActuator.h +++ b/source/gameengine/Converter/BL_ActionActuator.h @@ -49,8 +49,9 @@ public: short blendin, short priority, short end_reset, - float stride) - : SCA_IActuator(gameobj), + float stride, + PyTypeObject* T=&Type) + : SCA_IActuator(gameobj,T), m_lastpos(0, 0, 0), m_blendframe(0), @@ -112,6 +113,10 @@ public: KX_PYMETHOD_DOC(BL_ActionActuator,setChannel); + virtual PyObject* py_getattro(PyObject* attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject* attr, PyObject* value); + static PyObject* pyattr_get_action(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef); static int pyattr_set_action(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value); diff --git a/source/gameengine/Converter/BL_BlenderDataConversion.cpp b/source/gameengine/Converter/BL_BlenderDataConversion.cpp index 177f261e40b..b907e300879 100644 --- a/source/gameengine/Converter/BL_BlenderDataConversion.cpp +++ b/source/gameengine/Converter/BL_BlenderDataConversion.cpp @@ -163,6 +163,7 @@ extern "C" { #include "SG_BBox.h" #include "SG_Tree.h" +// defines USE_ODE to choose physics engine #include "KX_ConvertPhysicsObject.h" #ifdef USE_BULLET #include "CcdPhysicsEnvironment.h" @@ -1609,6 +1610,18 @@ void BL_CreatePhysicsObjectNew(KX_GameObject* gameobj, break; #endif +#ifdef USE_SUMO_SOLID + case UseSumo: + KX_ConvertSumoObject(gameobj, meshobj, kxscene, shapeprops, smmaterial, &objprop); + break; +#endif + +#ifdef USE_ODE + case UseODE: + KX_ConvertODEEngineObject(gameobj, meshobj, kxscene, shapeprops, smmaterial, &objprop); + break; +#endif //USE_ODE + case UseDynamo: //KX_ConvertDynamoObject(gameobj,meshobj,kxscene,shapeprops, smmaterial, &objprop); break; diff --git a/source/gameengine/Converter/BL_ShapeActionActuator.cpp b/source/gameengine/Converter/BL_ShapeActionActuator.cpp index 970539777f4..7aa8714de3a 100644 --- a/source/gameengine/Converter/BL_ShapeActionActuator.cpp +++ b/source/gameengine/Converter/BL_ShapeActionActuator.cpp @@ -427,17 +427,20 @@ PyTypeObject BL_ShapeActionActuator::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &SCA_IActuator::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods }; +PyParentObject BL_ShapeActionActuator::Parents[] = { + &BL_ShapeActionActuator::Type, + &SCA_IActuator::Type, + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL +}; PyMethodDef BL_ShapeActionActuator::Methods[] = { {"setAction", (PyCFunction) BL_ShapeActionActuator::sPySetAction, METH_VARARGS, (PY_METHODCHAR)SetAction_doc}, @@ -477,6 +480,19 @@ PyAttributeDef BL_ShapeActionActuator::Attributes[] = { { NULL } //Sentinel }; + +PyObject* BL_ShapeActionActuator::py_getattro(PyObject* attr) { + py_getattro_up(SCA_IActuator); +} + +PyObject* BL_ShapeActionActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int BL_ShapeActionActuator::py_setattro(PyObject *attr, PyObject* value) { + py_setattro_up(SCA_IActuator); +} + /* setStart */ const char BL_ShapeActionActuator::GetAction_doc[] = "getAction()\n" @@ -485,7 +501,7 @@ const char BL_ShapeActionActuator::GetAction_doc[] = PyObject* BL_ShapeActionActuator::PyGetAction() { ShowDeprecationWarning("getAction()", "the action property"); if (m_action){ - return PyUnicode_FromString(m_action->id.name+2); + return PyString_FromString(m_action->id.name+2); } Py_RETURN_NONE; } @@ -844,21 +860,21 @@ PyObject* BL_ShapeActionActuator::PySetType(PyObject* args) { PyObject* BL_ShapeActionActuator::pyattr_get_action(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { BL_ShapeActionActuator* self= static_cast<BL_ShapeActionActuator*>(self_v); - return PyUnicode_FromString(self->GetAction() ? self->GetAction()->id.name+2 : ""); + return PyString_FromString(self->GetAction() ? self->GetAction()->id.name+2 : ""); } int BL_ShapeActionActuator::pyattr_set_action(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) { BL_ShapeActionActuator* self= static_cast<BL_ShapeActionActuator*>(self_v); /* exact copy of BL_ActionActuator's function from here down */ - if (!PyUnicode_Check(value)) + if (!PyString_Check(value)) { PyErr_SetString(PyExc_ValueError, "actuator.action = val: Shape Action Actuator, expected the string name of the action"); return PY_SET_ATTR_FAIL; } bAction *action= NULL; - STR_String val = _PyUnicode_AsString(value); + STR_String val = PyString_AsString(value); if (val != "") { diff --git a/source/gameengine/Converter/BL_ShapeActionActuator.h b/source/gameengine/Converter/BL_ShapeActionActuator.h index 890fe3f9de9..d268eef6d23 100644 --- a/source/gameengine/Converter/BL_ShapeActionActuator.h +++ b/source/gameengine/Converter/BL_ShapeActionActuator.h @@ -50,8 +50,9 @@ public: short playtype, short blendin, short priority, - float stride) - : SCA_IActuator(gameobj), + float stride, + PyTypeObject* T=&Type) + : SCA_IActuator(gameobj,T), m_lastpos(0, 0, 0), m_blendframe(0), @@ -105,6 +106,10 @@ public: KX_PYMETHOD_DOC_NOARGS(BL_ShapeActionActuator,GetType); KX_PYMETHOD_DOC_VARARGS(BL_ShapeActionActuator,SetType); + virtual PyObject* py_getattro(PyObject* attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject* attr, PyObject* value); + static PyObject* pyattr_get_action(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef); static int pyattr_set_action(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value); diff --git a/source/gameengine/Converter/KX_BlenderSceneConverter.cpp b/source/gameengine/Converter/KX_BlenderSceneConverter.cpp index 9e0a710f44f..86e20b88580 100644 --- a/source/gameengine/Converter/KX_BlenderSceneConverter.cpp +++ b/source/gameengine/Converter/KX_BlenderSceneConverter.cpp @@ -44,12 +44,21 @@ #include "DummyPhysicsEnvironment.h" +//to decide to use sumo/ode or dummy physics - defines USE_ODE #include "KX_ConvertPhysicsObject.h" #ifdef USE_BULLET #include "CcdPhysicsEnvironment.h" #endif +#ifdef USE_ODE +#include "OdePhysicsEnvironment.h" +#endif //USE_ODE + +#ifdef USE_SUMO_SOLID +#include "SumoPhysicsEnvironment.h" +#endif + #include "KX_BlenderSceneConverter.h" #include "KX_BlenderScalarInterpolator.h" #include "BL_BlenderDataConversion.h" @@ -136,6 +145,10 @@ KX_BlenderSceneConverter::~KX_BlenderSceneConverter() delete (*itm).second; itm++; } + +#ifdef USE_SUMO_SOLID + KX_ClearSumoSharedShapes(); +#endif #ifdef USE_BULLET KX_ClearBulletSharedShapes(); @@ -318,7 +331,20 @@ void KX_BlenderSceneConverter::ConvertScene(const STR_String& scenename, destinationscene->SetPhysicsEnvironment(ccdPhysEnv); break; } -#endif +#endif + +#ifdef USE_SUMO_SOLID + case UseSumo: + destinationscene ->SetPhysicsEnvironment(new SumoPhysicsEnvironment()); + break; +#endif +#ifdef USE_ODE + + case UseODE: + destinationscene ->SetPhysicsEnvironment(new ODEPhysicsEnvironment()); + break; +#endif //USE_ODE + case UseDynamo: { } diff --git a/source/gameengine/Converter/Makefile b/source/gameengine/Converter/Makefile index ed95aa968c7..abded70f289 100644 --- a/source/gameengine/Converter/Makefile +++ b/source/gameengine/Converter/Makefile @@ -39,7 +39,8 @@ CPPFLAGS += -I$(OPENGL_HEADERS) CPPFLAGS += -I$(NAN_STRING)/include CPPFLAGS += -I$(NAN_SOUNDSYSTEM)/include CPPFLAGS += -I$(NAN_PYTHON)/include/python$(NAN_PYTHON_VERSION) -CPPFLAGS += -I$(NAN_FUZZICS)/include -I$(NAN_MOTO)/include +CPPFLAGS += -I$(NAN_FUZZICS)/include -I$(NAN_SUMO) -I$(NAN_MOTO)/include +CPPFLAGS += -I$(NAN_SOLID)/include CPPFLAGS += -I$(NAN_BULLET2)/include CPPFLAGS += -I../../blender diff --git a/source/gameengine/Converter/SConscript b/source/gameengine/Converter/SConscript index 05ea01c902a..3e0929e605a 100644 --- a/source/gameengine/Converter/SConscript +++ b/source/gameengine/Converter/SConscript @@ -21,6 +21,11 @@ incs += ' #source/blender/misc #source/blender/blenloader #source/blender/gpu' incs += ' #source/blender/windowmanager' incs += ' #source/blender/makesrna' +if env['WITH_BF_SOLID']: + incs += ' #source/gameengine/Physics/Sumo #source/gameengine/Physics/Sumo/Fuzzics/include' + incs += ' ' + env['BF_SOLID_INC'] + defs.append('USE_SUMO_SOLID') + incs += ' ' + env['BF_PYTHON_INC'] incs += ' ' + env['BF_BULLET_INC'] diff --git a/source/gameengine/Expressions/BoolValue.cpp b/source/gameengine/Expressions/BoolValue.cpp index 6779c2ea780..d90da8b3a92 100644 --- a/source/gameengine/Expressions/BoolValue.cpp +++ b/source/gameengine/Expressions/BoolValue.cpp @@ -29,6 +29,7 @@ const STR_String CBoolValue::sTrueString = "TRUE"; const STR_String CBoolValue::sFalseString = "FALSE"; + CBoolValue::CBoolValue() /* pre: false @@ -209,5 +210,5 @@ CValue* CBoolValue::GetReplica() PyObject* CBoolValue::ConvertValueToPython() { - return PyBool_FromLong(m_bool != 0); + return PyInt_FromLong(m_bool != 0); } diff --git a/source/gameengine/Expressions/CMakeLists.txt b/source/gameengine/Expressions/CMakeLists.txt index dffd13f64ff..e3942b46557 100644 --- a/source/gameengine/Expressions/CMakeLists.txt +++ b/source/gameengine/Expressions/CMakeLists.txt @@ -32,7 +32,6 @@ SET(INC ../../../intern/string ../../../intern/moto/include ../../../source/gameengine/SceneGraph - ../../../source/blender/blenloader ${PYTHON_INC} ) diff --git a/source/gameengine/Expressions/IntValue.cpp b/source/gameengine/Expressions/IntValue.cpp index b782de4bef6..227518e9439 100644 --- a/source/gameengine/Expressions/IntValue.cpp +++ b/source/gameengine/Expressions/IntValue.cpp @@ -330,7 +330,7 @@ void CIntValue::SetValue(CValue* newval) PyObject* CIntValue::ConvertValueToPython() { if((m_int > INT_MIN) && (m_int < INT_MAX)) - return PyLong_FromSsize_t(m_int); + return PyInt_FromLong(m_int); else return PyLong_FromLongLong(m_int); } diff --git a/source/gameengine/Expressions/KX_Python.h b/source/gameengine/Expressions/KX_Python.h index 61f7ef05042..b8006fdf0ed 100644 --- a/source/gameengine/Expressions/KX_Python.h +++ b/source/gameengine/Expressions/KX_Python.h @@ -32,8 +32,6 @@ //#define USE_DL_EXPORT #include "Python.h" -#define USE_MATHUTILS // Blender 2.5x api will use mathutils, for a while we might want to test without it - #ifdef __FreeBSD__ #include <osreldate.h> #if __FreeBSD_version > 500039 diff --git a/source/gameengine/Expressions/ListValue.cpp b/source/gameengine/Expressions/ListValue.cpp index 38b00dcc8fb..59344ddb7b7 100644 --- a/source/gameengine/Expressions/ListValue.cpp +++ b/source/gameengine/Expressions/ListValue.cpp @@ -76,9 +76,9 @@ PyObject* listvalue_mapping_subscript(PyObject* self, PyObject* pyindex) return NULL; } - if (PyUnicode_Check(pyindex)) + if (PyString_Check(pyindex)) { - CValue *item = ((CListValue*) list)->FindValue(_PyUnicode_AsString(pyindex)); + CValue *item = ((CListValue*) list)->FindValue(PyString_AsString(pyindex)); if (item) { PyObject* pyobj = item->ConvertValueToPython(); if(pyobj) @@ -87,14 +87,14 @@ PyObject* listvalue_mapping_subscript(PyObject* self, PyObject* pyindex) return item->GetProxy(); } } - else if (PyLong_Check(pyindex)) + else if (PyInt_Check(pyindex)) { - int index = PyLong_AsSsize_t(pyindex); + int index = PyInt_AsLong(pyindex); return listvalue_buffer_item(self, index); /* wont add a ref */ } PyObject *pyindex_str = PyObject_Repr(pyindex); /* new ref */ - PyErr_Format(PyExc_KeyError, "CList[key]: '%s' key not in list", _PyUnicode_AsString(pyindex_str)); + PyErr_Format(PyExc_KeyError, "CList[key]: '%s' key not in list", PyString_AsString(pyindex_str)); Py_DECREF(pyindex_str); return NULL; } @@ -220,12 +220,12 @@ static int listvalue_buffer_contains(PyObject *self_v, PyObject *value) return -1; } - if (PyUnicode_Check(value)) { - if (self->FindValue((const char *)_PyUnicode_AsString(value))) { + if (PyString_Check(value)) { + if (self->FindValue((const char *)PyString_AsString(value))) { return 1; } } - else if (PyObject_TypeCheck(value, &CValue::Type)) { /* not dict like at all but this worked before __contains__ was used */ + else if (BGE_PROXY_CHECK_TYPE(value)) { /* not dict like at all but this worked before __contains__ was used */ CValue *item= static_cast<CValue *>(BGE_PROXY_REF(value)); for (int i=0; i < self->GetCount(); i++) if (self->GetValue(i) == item) // Com @@ -289,19 +289,25 @@ PyTypeObject CListValue::Type = { 0, /*tp_hash*/ 0, /*tp_call */ 0, - NULL, - NULL, + py_base_getattro, + py_base_setattro, 0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, + Py_TPFLAGS_DEFAULT, 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + + +PyParentObject CListValue::Parents[] = { + &CListValue::Type, &CValue::Type, - 0,0,0,0,0,0, - py_base_new + NULL }; + + + PyMethodDef CListValue::Methods[] = { /* List style access */ {"append", (PyCFunction)CListValue::sPyappend,METH_O}, @@ -323,12 +329,21 @@ PyAttributeDef CListValue::Attributes[] = { { NULL } //Sentinel }; +PyObject* CListValue::py_getattro(PyObject* attr) { + py_getattro_up(CValue); +} + +PyObject* CListValue::py_getattro_dict() { + py_getattro_dict_up(CValue); +} + + ////////////////////////////////////////////////////////////////////// // Construction/Destruction ////////////////////////////////////////////////////////////////////// -CListValue::CListValue() -: CPropValue() +CListValue::CListValue(PyTypeObject *T ) +: CPropValue(T) { m_bReleaseContents=true; } @@ -544,7 +559,7 @@ PyObject* CListValue::Pyindex(PyObject *value) CValue* elem = GetValue(i); if (checkobj==elem || CheckEqual(checkobj,elem)) { - result = PyLong_FromSsize_t(i); + result = PyInt_FromLong(i); break; } } @@ -567,7 +582,7 @@ PyObject* CListValue::Pycount(PyObject* value) if (checkobj==NULL) { /* in this case just return that there are no items in the list */ PyErr_Clear(); - return PyLong_FromSsize_t(0); + return PyInt_FromLong(0); } int numelem = GetCount(); @@ -581,7 +596,7 @@ PyObject* CListValue::Pycount(PyObject* value) } checkobj->Release(); - return PyLong_FromSsize_t(numfound); + return PyInt_FromLong(numfound); } /* Matches python dict.get(key, [default]) */ @@ -608,7 +623,7 @@ PyObject* CListValue::Pyget(PyObject *args) /* Matches python dict.has_key() */ PyObject* CListValue::Pyhas_key(PyObject* value) { - if (PyUnicode_Check(value) && FindValue((const char *)_PyUnicode_AsString(value))) + if (PyString_Check(value) && FindValue((const char *)PyString_AsString(value))) Py_RETURN_TRUE; Py_RETURN_FALSE; diff --git a/source/gameengine/Expressions/ListValue.h b/source/gameengine/Expressions/ListValue.h index 98e6f216f11..68e900e25e0 100644 --- a/source/gameengine/Expressions/ListValue.h +++ b/source/gameengine/Expressions/ListValue.h @@ -24,7 +24,7 @@ class CListValue : public CPropValue //PLUGIN_DECLARE_SERIAL (CListValue,CValue) public: - CListValue(); + CListValue(PyTypeObject *T = &Type); virtual ~CListValue(); void AddConfigurationData(CValue* menuvalue); @@ -60,6 +60,8 @@ public: bool CheckEqual(CValue* first,CValue* second); + virtual PyObject* py_getattro(PyObject* attr); + virtual PyObject* py_getattro_dict(); virtual PyObject* py_repr(void) { PyObject *py_proxy= this->GetProxy(); PyObject *py_list= PySequence_List(py_proxy); diff --git a/source/gameengine/Expressions/Makefile b/source/gameengine/Expressions/Makefile index 09512c3ae87..f46c0037200 100644 --- a/source/gameengine/Expressions/Makefile +++ b/source/gameengine/Expressions/Makefile @@ -37,7 +37,6 @@ CCFLAGS += $(LEVEL_1_CPP_WARNINGS) CPPFLAGS += -I$(NAN_PYTHON)/include/python$(NAN_PYTHON_VERSION) CPPFLAGS += -I../../blender/makesdna -CPPFLAGS += -I$(NAN_GUARDEDALLOC)/include CPPFLAGS += -I$(NAN_STRING)/include CPPFLAGS += -I$(NAN_MOTO)/include diff --git a/source/gameengine/Expressions/PyObjectPlus.cpp b/source/gameengine/Expressions/PyObjectPlus.cpp index 475953749de..defb6853e67 100644 --- a/source/gameengine/Expressions/PyObjectPlus.cpp +++ b/source/gameengine/Expressions/PyObjectPlus.cpp @@ -74,13 +74,11 @@ PyTypeObject PyObjectPlus::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - NULL // no subtype + Methods }; @@ -93,88 +91,6 @@ PyObjectPlus::~PyObjectPlus() // assert(ob_refcnt==0); } - -PyObject *PyObjectPlus::py_base_repr(PyObject *self) // This should be the entry in Type. -{ - PyObjectPlus *self_plus= BGE_PROXY_REF(self); - if(self_plus==NULL) { - PyErr_SetString(PyExc_SystemError, BGE_PROXY_ERROR_MSG); - return NULL; - } - - return self_plus->py_repr(); -} - - -PyObject * PyObjectPlus::py_base_new(PyTypeObject *type, PyObject *args, PyObject *kwds) -{ - PyTypeObject *base_type; - PyObjectPlus_Proxy *base = NULL; - - if (!PyArg_ParseTuple(args, "O:Base PyObjectPlus", &base)) - return NULL; - - /* the 'base' PyObject may be subclassed (multiple times even) - * we need to find the first C++ defined class to check 'type' - * is a subclass of the base arguments type. - * - * This way we can share one tp_new function for every PyObjectPlus - * - * eg. - * - * # CustomOb is called 'type' in this C code - * class CustomOb(GameTypes.KX_GameObject): - * pass - * - * # this calls py_base_new(...), the type of 'CustomOb' is checked to be a subclass of the 'cont.owner' type - * ob = CustomOb(cont.owner) - * - * */ - base_type= Py_TYPE(base); - while(base_type && !BGE_PROXY_CHECK_TYPE(base_type)) - base_type= base_type->tp_base; - - if(base_type==NULL || !BGE_PROXY_CHECK_TYPE(base_type)) { - PyErr_SetString(PyExc_TypeError, "can't subclass from a blender game type because the argument given is not a game class or subclass"); - return NULL; - } - - /* use base_type rather then Py_TYPE(base) because we could alredy be subtyped */ - if(!PyType_IsSubtype(type, base_type)) { - PyErr_Format(PyExc_TypeError, "can't subclass blender game type <%s> from <%s> because it is not a subclass", base_type->tp_name, type->tp_name); - return NULL; - } - - /* invalidate the existing base and return a new subclassed one, - * this is a bit dodgy in that it also attaches its self to the existing object - * which is not really 'correct' python OO but for our use its OK. */ - - PyObjectPlus_Proxy *ret = (PyObjectPlus_Proxy *) type->tp_alloc(type, 0); /* starts with 1 ref, used for the return ref' */ - ret->ref= base->ref; - base->ref= NULL; /* invalidate! disallow further access */ - - ret->py_owns= base->py_owns; - - ret->ref->m_proxy= NULL; - - /* 'base' may be free'd after this func finished but not necessarily - * there is no reference to the BGE data now so it will throw an error on access */ - Py_DECREF(base); - - ret->ref->m_proxy= (PyObject *)ret; /* no need to add a ref because one is added when creating. */ - Py_INCREF(ret); /* we return a new ref but m_proxy holds a ref so we need to add one */ - - - /* 'ret' will have 2 references. - * - One ref is needed because ret->ref->m_proxy holds a refcount to the current proxy. - * - Another is needed for returning the value. - * - * So we should be ok with 2 refs, but for some reason this crashes. so adding a new ref... - * */ - - return (PyObject *)ret; -} - void PyObjectPlus::py_base_dealloc(PyObject *self) // python wrapper { PyObjectPlus *self_plus= BGE_PROXY_REF(self); @@ -183,56 +99,143 @@ void PyObjectPlus::py_base_dealloc(PyObject *self) // python wrapper self_plus->m_proxy = NULL; /* Need this to stop ~PyObjectPlus from decrefing m_proxy otherwise its decref'd twice and py-debug crashes */ delete self_plus; } - + BGE_PROXY_REF(self)= NULL; // not really needed } - -#if 0 - /* is ok normally but not for subtyping, use tp_free instead. */ PyObject_DEL( self ); -#else - Py_TYPE(self)->tp_free(self); -#endif }; -PyObjectPlus::PyObjectPlus() : SG_QList() // constructor +PyObjectPlus::PyObjectPlus(PyTypeObject *T) : SG_QList() // constructor { + MT_assert(T != NULL); m_proxy= NULL; }; - + /*------------------------------ * PyObjectPlus Methods -- Every class, even the abstract one should have a Methods ------------------------------*/ PyMethodDef PyObjectPlus::Methods[] = { + {"isA", (PyCFunction) sPyisA, METH_O}, {NULL, NULL} /* Sentinel */ }; -#define attr_invalid (&(PyObjectPlus::Attributes[0])) PyAttributeDef PyObjectPlus::Attributes[] = { KX_PYATTRIBUTE_RO_FUNCTION("invalid", PyObjectPlus, pyattr_get_invalid), {NULL} //Sentinel }; +PyObject* PyObjectPlus::pyattr_get_invalid(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) +{ + Py_RETURN_FALSE; +} +/*------------------------------ + * PyObjectPlus Parents -- Every class, even the abstract one should have parents +------------------------------*/ +PyParentObject PyObjectPlus::Parents[] = {&PyObjectPlus::Type, NULL}; -PyObject* PyObjectPlus::pyattr_get_invalid(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) +/*------------------------------ + * PyObjectPlus attributes -- attributes +------------------------------*/ + + +/* This should be the entry in Type since it takes the C++ class from PyObjectPlus_Proxy */ +PyObject *PyObjectPlus::py_base_getattro(PyObject * self, PyObject *attr) { - return PyBool_FromLong(self_v ? 1:0); + PyObjectPlus *self_plus= BGE_PROXY_REF(self); + if(self_plus==NULL) { + if(!strcmp("invalid", PyString_AsString(attr))) { + Py_RETURN_TRUE; + } + PyErr_SetString(PyExc_SystemError, BGE_PROXY_ERROR_MSG); + return NULL; + } + + PyObject *ret= self_plus->py_getattro(attr); + + /* Attribute not found, was this a __dict__ lookup?, otherwise set an error if none is set */ + if(ret==NULL) { + char *attr_str= PyString_AsString(attr); + + if (strcmp(attr_str, "__dict__")==0) + { + /* the error string will probably not + * be set but just incase clear it */ + PyErr_Clear(); + ret= self_plus->py_getattro_dict(); + } + else if (!PyErr_Occurred()) { + /* We looked for an attribute but it wasnt found + * since py_getattro didnt set the error, set it here */ + PyErr_Format(PyExc_AttributeError, "'%s' object has no attribute '%s'", self->ob_type->tp_name, attr_str); + } + } + return ret; } -/* note, this is called as a python 'getset, where the PyAttributeDef is the closure */ -PyObject *PyObjectPlus::py_get_attrdef(PyObject *self_py, const PyAttributeDef *attrdef) +/* This should be the entry in Type since it takes the C++ class from PyObjectPlus_Proxy */ +int PyObjectPlus::py_base_setattro(PyObject *self, PyObject *attr, PyObject *value) { - void *self= (void *)(BGE_PROXY_REF(self_py)); - if(self==NULL) { - if(attrdef == attr_invalid) - Py_RETURN_TRUE; // dont bother running the function + PyObjectPlus *self_plus= BGE_PROXY_REF(self); + if(self_plus==NULL) { + PyErr_SetString(PyExc_SystemError, BGE_PROXY_ERROR_MSG); + return -1; + } + + if (value==NULL) + return self_plus->py_delattro(attr); + + return self_plus->py_setattro(attr, value); +} +PyObject *PyObjectPlus::py_base_repr(PyObject *self) // This should be the entry in Type. +{ + + PyObjectPlus *self_plus= BGE_PROXY_REF(self); + if(self_plus==NULL) { PyErr_SetString(PyExc_SystemError, BGE_PROXY_ERROR_MSG); return NULL; } + + return self_plus->py_repr(); +} +PyObject *PyObjectPlus::py_getattro(PyObject* attr) +{ + PyObject *descr = PyDict_GetItem(Type.tp_dict, attr); \ + if (descr == NULL) { + return NULL; /* py_base_getattro sets the error, this way we can avoid setting the error at many levels */ + } else { + /* Copied from py_getattro_up */ + if (PyCObject_Check(descr)) { + return py_get_attrdef((void *)this, (const PyAttributeDef*)PyCObject_AsVoidPtr(descr)); + } else if (descr->ob_type->tp_descr_get) { + return PyCFunction_New(((PyMethodDescrObject *)descr)->d_method, this->m_proxy); + } else { + return NULL; + } + /* end py_getattro_up copy */ + } +} + +PyObject* PyObjectPlus::py_getattro_dict() { + return py_getattr_dict(NULL, Type.tp_dict); +} +int PyObjectPlus::py_delattro(PyObject* attr) +{ + PyErr_SetString(PyExc_AttributeError, "attribute cant be deleted"); + return 1; +} + +int PyObjectPlus::py_setattro(PyObject *attr, PyObject* value) +{ + PyErr_SetString(PyExc_AttributeError, "attribute cant be set"); + return PY_SET_ATTR_MISSING; +} + +PyObject *PyObjectPlus::py_get_attrdef(void *self, const PyAttributeDef *attrdef) +{ if (attrdef->m_type == KX_PYATTRIBUTE_TYPE_DUMMY) { // fake attribute, ignore @@ -256,14 +259,14 @@ PyObject *PyObjectPlus::py_get_attrdef(PyObject *self_py, const PyAttributeDef * { bool *val = reinterpret_cast<bool*>(ptr); ptr += sizeof(bool); - PyList_SET_ITEM(resultlist,i,PyLong_FromSsize_t(*val)); + PyList_SET_ITEM(resultlist,i,PyInt_FromLong(*val)); break; } case KX_PYATTRIBUTE_TYPE_SHORT: { short int *val = reinterpret_cast<short int*>(ptr); ptr += sizeof(short int); - PyList_SET_ITEM(resultlist,i,PyLong_FromSsize_t(*val)); + PyList_SET_ITEM(resultlist,i,PyInt_FromLong(*val)); break; } case KX_PYATTRIBUTE_TYPE_ENUM: @@ -278,7 +281,7 @@ PyObject *PyObjectPlus::py_get_attrdef(PyObject *self_py, const PyAttributeDef * { int *val = reinterpret_cast<int*>(ptr); ptr += sizeof(int); - PyList_SET_ITEM(resultlist,i,PyLong_FromSsize_t(*val)); + PyList_SET_ITEM(resultlist,i,PyInt_FromLong(*val)); break; } case KX_PYATTRIBUTE_TYPE_FLOAT: @@ -302,12 +305,12 @@ PyObject *PyObjectPlus::py_get_attrdef(PyObject *self_py, const PyAttributeDef * case KX_PYATTRIBUTE_TYPE_BOOL: { bool *val = reinterpret_cast<bool*>(ptr); - return PyLong_FromSsize_t(*val); + return PyInt_FromLong(*val); } case KX_PYATTRIBUTE_TYPE_SHORT: { short int *val = reinterpret_cast<short int*>(ptr); - return PyLong_FromSsize_t(*val); + return PyInt_FromLong(*val); } case KX_PYATTRIBUTE_TYPE_ENUM: // enum are like int, just make sure the field size is the same @@ -319,7 +322,7 @@ PyObject *PyObjectPlus::py_get_attrdef(PyObject *self_py, const PyAttributeDef * case KX_PYATTRIBUTE_TYPE_INT: { int *val = reinterpret_cast<int*>(ptr); - return PyLong_FromSsize_t(*val); + return PyInt_FromLong(*val); } case KX_PYATTRIBUTE_TYPE_FLOAT: { @@ -328,23 +331,18 @@ PyObject *PyObjectPlus::py_get_attrdef(PyObject *self_py, const PyAttributeDef * } case KX_PYATTRIBUTE_TYPE_VECTOR: { - MT_Vector3 *val = reinterpret_cast<MT_Vector3*>(ptr); -#ifdef USE_MATHUTILS - float fval[3]= {(*val)[0], (*val)[1], (*val)[2]}; - return newVectorObject(fval, 3, Py_NEW); -#else PyObject* resultlist = PyList_New(3); + MT_Vector3 *val = reinterpret_cast<MT_Vector3*>(ptr); for (unsigned int i=0; i<3; i++) { PyList_SET_ITEM(resultlist,i,PyFloat_FromDouble((*val)[i])); } return resultlist; -#endif } case KX_PYATTRIBUTE_TYPE_STRING: { STR_String *val = reinterpret_cast<STR_String*>(ptr); - return PyUnicode_FromString(*val); + return PyString_FromString(*val); } default: return NULL; @@ -352,15 +350,8 @@ PyObject *PyObjectPlus::py_get_attrdef(PyObject *self_py, const PyAttributeDef * } } -/* note, this is called as a python getset */ -int PyObjectPlus::py_set_attrdef(PyObject *self_py, PyObject *value, const PyAttributeDef *attrdef) +int PyObjectPlus::py_set_attrdef(void *self, const PyAttributeDef *attrdef, PyObject *value) { - void *self= (void *)(BGE_PROXY_REF(self_py)); - if(self==NULL) { - PyErr_SetString(PyExc_SystemError, BGE_PROXY_ERROR_MSG); - return PY_SET_ATTR_FAIL; - } - void *undoBuffer = NULL; void *sourceBuffer = NULL; size_t bufferSize = 0; @@ -425,9 +416,9 @@ int PyObjectPlus::py_set_attrdef(PyObject *self_py, PyObject *value, const PyAtt { bool *var = reinterpret_cast<bool*>(ptr); ptr += sizeof(bool); - if (PyLong_Check(item)) + if (PyInt_Check(item)) { - *var = (PyLong_AsSsize_t(item) != 0); + *var = (PyInt_AsLong(item) != 0); } else if (PyBool_Check(item)) { @@ -444,9 +435,9 @@ int PyObjectPlus::py_set_attrdef(PyObject *self_py, PyObject *value, const PyAtt { short int *var = reinterpret_cast<short int*>(ptr); ptr += sizeof(short int); - if (PyLong_Check(item)) + if (PyInt_Check(item)) { - long val = PyLong_AsSsize_t(item); + long val = PyInt_AsLong(item); if (attrdef->m_clamp) { if (val < attrdef->m_imin) @@ -480,9 +471,9 @@ int PyObjectPlus::py_set_attrdef(PyObject *self_py, PyObject *value, const PyAtt { int *var = reinterpret_cast<int*>(ptr); ptr += sizeof(int); - if (PyLong_Check(item)) + if (PyInt_Check(item)) { - long val = PyLong_AsSsize_t(item); + long val = PyInt_AsLong(item); if (attrdef->m_clamp) { if (val < attrdef->m_imin) @@ -615,9 +606,9 @@ int PyObjectPlus::py_set_attrdef(PyObject *self_py, PyObject *value, const PyAtt case KX_PYATTRIBUTE_TYPE_BOOL: { bool *var = reinterpret_cast<bool*>(ptr); - if (PyLong_Check(value)) + if (PyInt_Check(value)) { - *var = (PyLong_AsSsize_t(value) != 0); + *var = (PyInt_AsLong(value) != 0); } else if (PyBool_Check(value)) { @@ -633,9 +624,9 @@ int PyObjectPlus::py_set_attrdef(PyObject *self_py, PyObject *value, const PyAtt case KX_PYATTRIBUTE_TYPE_SHORT: { short int *var = reinterpret_cast<short int*>(ptr); - if (PyLong_Check(value)) + if (PyInt_Check(value)) { - long val = PyLong_AsSsize_t(value); + long val = PyInt_AsLong(value); if (attrdef->m_clamp) { if (val < attrdef->m_imin) @@ -668,9 +659,9 @@ int PyObjectPlus::py_set_attrdef(PyObject *self_py, PyObject *value, const PyAtt case KX_PYATTRIBUTE_TYPE_INT: { int *var = reinterpret_cast<int*>(ptr); - if (PyLong_Check(value)) + if (PyInt_Check(value)) { - long val = PyLong_AsSsize_t(value); + long val = PyInt_AsLong(value); if (attrdef->m_clamp) { if (val < attrdef->m_imin) @@ -755,9 +746,9 @@ int PyObjectPlus::py_set_attrdef(PyObject *self_py, PyObject *value, const PyAtt case KX_PYATTRIBUTE_TYPE_STRING: { STR_String *var = reinterpret_cast<STR_String*>(ptr); - if (PyUnicode_Check(value)) + if (PyString_Check(value)) { - char *val = _PyUnicode_AsString(value); + char *val = PyString_AsString(value); if (attrdef->m_clamp) { if (strlen(val) < attrdef->m_imin) @@ -838,6 +829,48 @@ PyObject *PyObjectPlus::py_repr(void) return NULL; } +/*------------------------------ + * PyObjectPlus isA -- the isA functions +------------------------------*/ +bool PyObjectPlus::isA(PyTypeObject *T) // if called with a Type, use "typename" +{ + int i; + PyParentObject P; + PyParentObject *Ps = GetParents(); + + for (P = Ps[i=0]; P != NULL; P = Ps[i++]) + if (P==T) + return true; + + return false; +} + + +bool PyObjectPlus::isA(const char *mytypename) // check typename of each parent +{ + int i; + PyParentObject P; + PyParentObject *Ps = GetParents(); + + for (P = Ps[i=0]; P != NULL; P = Ps[i++]) + if (strcmp(P->tp_name, mytypename)==0) + return true; + + return false; +} + +PyObject *PyObjectPlus::PyisA(PyObject *value) // Python wrapper for isA +{ + if (PyType_Check(value)) { + return PyBool_FromLong(isA((PyTypeObject *)value)); + } else if (PyString_Check(value)) { + return PyBool_FromLong(isA(PyString_AsString(value))); + } + PyErr_SetString(PyExc_TypeError, "object.isA(value): expected a type or a string"); + return NULL; +} + + void PyObjectPlus::ProcessReplica() { /* Clear the proxy, will be created again if needed with GetProxy() @@ -862,6 +895,27 @@ void PyObjectPlus::InvalidateProxy() // check typename of each parent } } +/* Utility function called by the macro py_getattro_up() + * for getting ob.__dict__() values from our PyObject + * this is used by python for doing dir() on an object, so its good + * if we return a list of attributes and methods. + * + * Other then making dir() useful the value returned from __dict__() is not useful + * since every value is a Py_None + * */ +PyObject *py_getattr_dict(PyObject *pydict, PyObject *tp_dict) +{ + if(pydict==NULL) { /* incase calling __dict__ on the parent of this object raised an error */ + PyErr_Clear(); + pydict = PyDict_New(); + } + + PyDict_Update(pydict, tp_dict); + return pydict; +} + + + PyObject *PyObjectPlus::GetProxy_Ext(PyObjectPlus *self, PyTypeObject *tp) { if (self->m_proxy==NULL) @@ -932,7 +986,7 @@ void PyObjectPlus::ShowDeprecationWarning_func(const char* old_way,const char* n co_filename= PyObject_GetAttrString(f_code, "co_filename"); if (co_filename) { - printf("\t%s:%d\n", _PyUnicode_AsString(co_filename), (int)PyLong_AsSsize_t(f_lineno)); + printf("\t%s:%d\n", PyString_AsString(co_filename), (int)PyInt_AsLong(f_lineno)); Py_DECREF(f_lineno); Py_DECREF(f_code); diff --git a/source/gameengine/Expressions/PyObjectPlus.h b/source/gameengine/Expressions/PyObjectPlus.h index a18df9d36a9..c002dccefe4 100644 --- a/source/gameengine/Expressions/PyObjectPlus.h +++ b/source/gameengine/Expressions/PyObjectPlus.h @@ -45,15 +45,21 @@ * Python defines ------------------------------*/ -#ifdef USE_MATHUTILS -extern "C" { -#include "../../blender/python/generic/Mathutils.h" /* so we can have mathutils callbacks */ -} + + +#if PY_VERSION_HEX > 0x03000000 +#define PyString_FromString PyUnicode_FromString +#define PyString_FromFormat PyUnicode_FromFormat +#define PyString_Check PyUnicode_Check +#define PyString_Size PyUnicode_GetSize + +#define PyInt_FromLong PyLong_FromSsize_t +#define PyInt_AsLong PyLong_AsSsize_t +#define PyString_AsString _PyUnicode_AsString +#define PyInt_Check PyLong_Check +#define PyInt_AS_LONG PyLong_AsLong // TODO - check this one #endif -extern "C" { -#include "../../blender/python/intern/bpy_compat.h" -} /* @@ -135,7 +141,7 @@ typedef struct { #define BGE_PROXY_PYOWNS(_self) (((PyObjectPlus_Proxy *)_self)->py_owns) /* Note, sometimes we dont care what BGE type this is as long as its a proxy */ -#define BGE_PROXY_CHECK_TYPE(_type) ((_type)->tp_dealloc == PyObjectPlus::py_base_dealloc) +#define BGE_PROXY_CHECK_TYPE(_self) ((_self)->ob_type->tp_dealloc == PyObjectPlus::py_base_dealloc) // This must be the first line of each @@ -145,10 +151,41 @@ typedef struct { static PyTypeObject Type; \ static PyMethodDef Methods[]; \ static PyAttributeDef Attributes[]; \ + static PyParentObject Parents[]; \ virtual PyTypeObject *GetType(void) {return &Type;}; \ + virtual PyParentObject *GetParents(void) {return Parents;} \ virtual PyObject *GetProxy() {return GetProxy_Ext(this, &Type);}; \ virtual PyObject *NewProxy(bool py_owns) {return NewProxy_Ext(this, &Type, py_owns);}; \ + + + + // This defines the py_getattro_up macro + // which allows attribute and method calls + // to be properly passed up the hierarchy. + // + // Note, PyDict_GetItem() WONT set an exception! + // let the py_base_getattro function do this. + +#define py_getattro_up(Parent) \ + \ + PyObject *descr = PyDict_GetItem(Type.tp_dict, attr); \ + \ + if(descr) { \ + if (PyCObject_Check(descr)) { \ + return py_get_attrdef((void *)this, (const PyAttributeDef*)PyCObject_AsVoidPtr(descr)); \ + } else if (descr->ob_type->tp_descr_get) { \ + return PyCFunction_New(((PyMethodDescrObject *)descr)->d_method, this->m_proxy); \ + } else { \ + return NULL; \ + } \ + } else { \ + return Parent::py_getattro(attr); \ + } + +#define py_getattro_dict_up(Parent) \ + return py_getattr_dict(Parent::py_getattro_dict(), Type.tp_dict); + /* * nonzero values are an error for setattr * however because of the nested lookups we need to know if the errors @@ -160,6 +197,29 @@ typedef struct { #define PY_SET_ATTR_MISSING -1 #define PY_SET_ATTR_SUCCESS 0 +#define py_setattro_up(Parent) \ + PyObject *descr = PyDict_GetItem(Type.tp_dict, attr); \ + \ + if(descr) { \ + if (PyCObject_Check(descr)) { \ + const PyAttributeDef* attrdef= reinterpret_cast<const PyAttributeDef *>(PyCObject_AsVoidPtr(descr)); \ + if (attrdef->m_access == KX_PYATTRIBUTE_RO) { \ + PyErr_Format(PyExc_AttributeError, "\"%s\" is read only", PyString_AsString(attr)); \ + return PY_SET_ATTR_FAIL; \ + } \ + else { \ + return py_set_attrdef((void *)this, attrdef, value); \ + } \ + } else { \ + PyErr_Format(PyExc_AttributeError, "\"%s\" cannot be set", PyString_AsString(attr)); \ + return PY_SET_ATTR_FAIL; \ + } \ + } else { \ + PyErr_Clear(); \ + return Parent::py_setattro(attr, value); \ + } + + /** * These macros are helpfull when embedding Python routines. The second * macro is one that also requires a documentation string @@ -429,7 +489,7 @@ class PyObjectPlus : public SG_QList Py_Header; // Always start with Py_Header public: - PyObjectPlus(); + PyObjectPlus(PyTypeObject *T); PyObject *m_proxy; /* actually a PyObjectPlus_Proxy */ @@ -437,19 +497,30 @@ public: /* These static functions are referenced by ALL PyObjectPlus_Proxy types * they take the C++ reference from the PyObjectPlus_Proxy and call - * its own virtual py_repr, py_base_dealloc ,etc. functions. + * its own virtual py_getattro, py_setattro etc. functions. */ - - static PyObject* py_base_new(PyTypeObject *type, PyObject *args, PyObject *kwds); /* allows subclassing */ static void py_base_dealloc(PyObject *self); + static PyObject* py_base_getattro(PyObject * self, PyObject *attr); + static int py_base_setattro(PyObject *self, PyObject *attr, PyObject *value); static PyObject* py_base_repr(PyObject *self); /* These are all virtual python methods that are defined in each class * Our own fake subclassing calls these on each class, then calls the parent */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_delattro(PyObject *attr); + virtual int py_setattro(PyObject *attr, PyObject *value); virtual PyObject* py_repr(void); - static PyObject* py_get_attrdef(PyObject *self_py, const PyAttributeDef *attrdef); - static int py_set_attrdef(PyObject *self_py, PyObject *value, const PyAttributeDef *attrdef); + static PyObject* py_get_attrdef(void *self, const PyAttributeDef *attrdef); + static int py_set_attrdef(void *self, const PyAttributeDef *attrdef, PyObject *value); + + /* isA() methods, shonky replacement for pythons issubclass() + * which we cant use because we have our own subclass system */ + bool isA(PyTypeObject *T); + bool isA(const char *mytypename); + + KX_PYMETHOD_O(PyObjectPlus,isA); /* Kindof dumb, always returns True, the false case is checked for, before this function gets accessed */ static PyObject* pyattr_get_invalid(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef); diff --git a/source/gameengine/Expressions/StringValue.h b/source/gameengine/Expressions/StringValue.h index c580e8fd23a..52f8a580f4d 100644 --- a/source/gameengine/Expressions/StringValue.h +++ b/source/gameengine/Expressions/StringValue.h @@ -40,7 +40,7 @@ public: virtual void SetValue(CValue* newval) { m_strString = newval->GetText(); SetModified(true); }; virtual CValue* GetReplica(); virtual PyObject* ConvertValueToPython() { - return PyUnicode_FromString(m_strString.Ptr()); + return PyString_FromString(m_strString.Ptr()); } private: diff --git a/source/gameengine/Expressions/Value.cpp b/source/gameengine/Expressions/Value.cpp index d8c81f56f66..61dabff510b 100644 --- a/source/gameengine/Expressions/Value.cpp +++ b/source/gameengine/Expressions/Value.cpp @@ -54,17 +54,15 @@ PyTypeObject CValue::Type = { py_base_repr, 0, 0,0,0,0,0, - NULL, - NULL, - 0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &PyObjectPlus::Type, - 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods +}; + +PyParentObject CValue::Parents[] = { + &CValue::Type, + NULL }; PyMethodDef CValue::Methods[] = { @@ -76,7 +74,7 @@ PyObject* CValue::PyGetName() { ShowDeprecationWarning("getName()", "the name property"); - return PyUnicode_FromString(this->GetName()); + return PyString_FromString(this->GetName()); } /*#define CVALUE_DEBUG*/ @@ -102,8 +100,8 @@ std::vector<SmartCValueRef> gRefList; //int gRefCountValue; #endif -CValue::CValue() - : PyObjectPlus(), +CValue::CValue(PyTypeObject *T) + : PyObjectPlus(T), #else CValue::CValue() : @@ -555,9 +553,33 @@ PyAttributeDef CValue::Attributes[] = { { NULL } //Sentinel }; + +PyObject* CValue::py_getattro(PyObject *attr) +{ + char *attr_str= PyString_AsString(attr); + CValue* resultattr = GetProperty(attr_str); + if (resultattr) + { + /* only show the wanting here because python inspects for __class__ and KX_MeshProxy uses CValues name attr */ + ShowDeprecationWarning("val = ob.attr", "val = ob['attr']"); + + PyObject* pyconvert = resultattr->ConvertValueToPython(); + + if (pyconvert) + return pyconvert; + else + return resultattr->GetProxy(); + } + py_getattro_up(PyObjectPlus); +} + +PyObject* CValue::py_getattro_dict() { + py_getattro_dict_up(PyObjectPlus); +} + PyObject * CValue::pyattr_get_name(void * self_v, const KX_PYATTRIBUTE_DEF * attrdef) { CValue * self = static_cast<CValue *> (self_v); - return PyUnicode_FromString(self->GetName()); + return PyString_FromString(self->GetName()); } CValue* CValue::ConvertPythonToValue(PyObject* pyobj, const char *error_prefix) @@ -601,23 +623,30 @@ CValue* CValue::ConvertPythonToValue(PyObject* pyobj, const char *error_prefix) { vallie = new CFloatValue( (float)PyFloat_AsDouble(pyobj) ); } else -#if PY_VERSION_HEX < 0x03000000 if (PyInt_Check(pyobj)) { vallie = new CIntValue( (cInt)PyInt_AS_LONG(pyobj) ); } else -#endif if (PyLong_Check(pyobj)) { vallie = new CIntValue( (cInt)PyLong_AsLongLong(pyobj) ); } else - if (PyUnicode_Check(pyobj)) + if (PyString_Check(pyobj)) { - vallie = new CStringValue(_PyUnicode_AsString(pyobj),""); + vallie = new CStringValue(PyString_AsString(pyobj),""); } else - if (PyObject_TypeCheck(pyobj, &CValue::Type)) /* Note, dont let these get assigned to GameObject props, must check elsewhere */ + if (BGE_PROXY_CHECK_TYPE(pyobj)) /* Note, dont let these get assigned to GameObject props, must check elsewhere */ { - vallie = (static_cast<CValue *>(BGE_PROXY_REF(pyobj)))->AddRef(); + if (BGE_PROXY_REF(pyobj) && (BGE_PROXY_REF(pyobj))->isA(&CValue::Type)) + { + vallie = (static_cast<CValue *>(BGE_PROXY_REF(pyobj)))->AddRef(); + } else { + + if(BGE_PROXY_REF(pyobj)) /* this is not a CValue */ + PyErr_Format(PyExc_TypeError, "%sgame engine python type cannot be used as a property", error_prefix); + else /* PyObjectPlus_Proxy has been removed, cant use */ + PyErr_Format(PyExc_SystemError, "%s"BGE_PROXY_ERROR_MSG, error_prefix); + } } else { /* return an error value from the caller */ @@ -627,6 +656,57 @@ CValue* CValue::ConvertPythonToValue(PyObject* pyobj, const char *error_prefix) } +int CValue::py_delattro(PyObject *attr) +{ + ShowDeprecationWarning("del ob.attr", "del ob['attr']"); + + char *attr_str= PyString_AsString(attr); + if (RemoveProperty(attr_str)) + return 0; + + PyErr_Format(PyExc_AttributeError, "attribute \"%s\" dosnt exist", attr_str); + return PY_SET_ATTR_MISSING; +} + +int CValue::py_setattro(PyObject *attr, PyObject* pyobj) +{ + ShowDeprecationWarning("ob.attr = val", "ob['attr'] = val"); + + char *attr_str= PyString_AsString(attr); + CValue* oldprop = GetProperty(attr_str); + CValue* vallie; + + /* Dissallow python to assign GameObjects, Scenes etc as values */ + if ((BGE_PROXY_CHECK_TYPE(pyobj)==0) && (vallie = ConvertPythonToValue(pyobj, "cvalue.attr = value: "))) + { + if (oldprop) + oldprop->SetValue(vallie); + else + SetProperty(attr_str, vallie); + + vallie->Release(); + } + else { + // ConvertPythonToValue sets the error message + // must return missing so KX_GameObect knows this + // attribute was not a function or bult in attribute, + // + // CValue attributes override internal attributes + // so if it exists as a CValue attribute already, + // assume your trying to set it to a differnt CValue attribute + // otherwise return PY_SET_ATTR_MISSING so children + // classes know they can set it without conflict + + if (GetProperty(attr_str)) + return PY_SET_ATTR_COERCE_FAIL; /* failed to set an existing attribute */ + else + return PY_SET_ATTR_MISSING; /* allow the KX_GameObject dict to set */ + } + + //PyObjectPlus::py_setattro(attr,value); + return PY_SET_ATTR_SUCCESS; +}; + PyObject* CValue::ConvertKeysToPython( void ) { PyObject *pylist = PyList_New( 0 ); @@ -637,7 +717,7 @@ PyObject* CValue::ConvertKeysToPython( void ) std::map<STR_String,CValue*>::iterator it; for (it= m_pNamedPropertyArray->begin(); (it != m_pNamedPropertyArray->end()); it++) { - pystr = PyUnicode_FromString( (*it).first ); + pystr = PyString_FromString( (*it).first ); PyList_Append(pylist, pystr); Py_DECREF( pystr ); } diff --git a/source/gameengine/Expressions/Value.h b/source/gameengine/Expressions/Value.h index 8c9f99b335e..29ef19b46c9 100644 --- a/source/gameengine/Expressions/Value.h +++ b/source/gameengine/Expressions/Value.h @@ -215,18 +215,26 @@ public: // Construction / Destruction #ifndef NO_EXP_PYTHON_EMBEDDING - CValue(); + CValue(PyTypeObject *T = &Type); //static PyObject* PyMake(PyObject*,PyObject*); virtual PyObject *py_repr(void) { - return PyUnicode_FromString((const char*)GetText()); + return PyString_FromString((const char*)GetText()); } + + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); virtual PyObject* ConvertValueToPython() { return NULL; } virtual CValue* ConvertPythonToValue(PyObject* pyobj, const char *error_prefix); + + + virtual int py_delattro(PyObject *attr); + virtual int py_setattro(PyObject *attr, PyObject* value); static PyObject * pyattr_get_name(void * self, const KX_PYATTRIBUTE_DEF * attrdef); @@ -409,8 +417,8 @@ class CPropValue : public CValue public: #ifndef NO_EXP_PYTHON_EMBEDDING - CPropValue() : - CValue(), + CPropValue(PyTypeObject* T=&Type) : + CValue(T), #else CPropValue() : #endif //NO_EXP_PYTHON_EMBEDDING diff --git a/source/gameengine/GameLogic/SCA_2DFilterActuator.cpp b/source/gameengine/GameLogic/SCA_2DFilterActuator.cpp index 04d46e259d3..caed85b9938 100644 --- a/source/gameengine/GameLogic/SCA_2DFilterActuator.cpp +++ b/source/gameengine/GameLogic/SCA_2DFilterActuator.cpp @@ -42,8 +42,9 @@ SCA_2DFilterActuator::SCA_2DFilterActuator( float float_arg, int int_arg, RAS_IRasterizer* rasterizer, - RAS_IRenderTools* rendertools) - : SCA_IActuator(gameobj), + RAS_IRenderTools* rendertools, + PyTypeObject* T) + : SCA_IActuator(gameobj, T), m_type(type), m_disableMotionBlur(flag), m_float_arg(float_arg), @@ -123,17 +124,23 @@ PyTypeObject SCA_2DFilterActuator::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &SCA_IActuator::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods }; + +PyParentObject SCA_2DFilterActuator::Parents[] = { + &SCA_2DFilterActuator::Type, + &SCA_IActuator::Type, + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL +}; + + PyMethodDef SCA_2DFilterActuator::Methods[] = { /* add python functions to deal with m_msg... */ {NULL,NULL} @@ -147,3 +154,18 @@ PyAttributeDef SCA_2DFilterActuator::Attributes[] = { KX_PYATTRIBUTE_FLOAT_RW("value", 0.0, 100.0, SCA_2DFilterActuator, m_float_arg), { NULL } //Sentinel }; + +PyObject* SCA_2DFilterActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* SCA_2DFilterActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int SCA_2DFilterActuator::py_setattro(PyObject *attr, PyObject* value) +{ + py_setattro_up(SCA_IActuator); +} + diff --git a/source/gameengine/GameLogic/SCA_2DFilterActuator.h b/source/gameengine/GameLogic/SCA_2DFilterActuator.h index c357c4f3e37..13b9997a010 100644 --- a/source/gameengine/GameLogic/SCA_2DFilterActuator.h +++ b/source/gameengine/GameLogic/SCA_2DFilterActuator.h @@ -56,12 +56,23 @@ public: float float_arg, int int_arg, RAS_IRasterizer* rasterizer, - RAS_IRenderTools* rendertools); + RAS_IRenderTools* rendertools, + PyTypeObject* T=&Type + ); void SetShaderText(const char *text); virtual ~SCA_2DFilterActuator(); virtual bool Update(); virtual CValue* GetReplica(); + + /* --------------------------------------------------------------------- */ + /* Python interface ---------------------------------------------------- */ + /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); + }; #endif diff --git a/source/gameengine/GameLogic/SCA_ANDController.cpp b/source/gameengine/GameLogic/SCA_ANDController.cpp index 78e1350428e..87f7c612e7c 100644 --- a/source/gameengine/GameLogic/SCA_ANDController.cpp +++ b/source/gameengine/GameLogic/SCA_ANDController.cpp @@ -42,9 +42,10 @@ /* Native functions */ /* ------------------------------------------------------------------------- */ -SCA_ANDController::SCA_ANDController(SCA_IObject* gameobj) +SCA_ANDController::SCA_ANDController(SCA_IObject* gameobj, + PyTypeObject* T) : - SCA_IController(gameobj) + SCA_IController(gameobj,T) { } @@ -115,15 +116,19 @@ PyTypeObject SCA_ANDController::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_ANDController::Parents[] = { + &SCA_ANDController::Type, &SCA_IController::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_ANDController::Methods[] = { @@ -134,4 +139,12 @@ PyAttributeDef SCA_ANDController::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_ANDController::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IController); +} + +PyObject* SCA_ANDController::py_getattro_dict() { + py_getattro_dict_up(SCA_IController); +} + /* eof */ diff --git a/source/gameengine/GameLogic/SCA_ANDController.h b/source/gameengine/GameLogic/SCA_ANDController.h index cb16d7fca01..9a359d57cb4 100644 --- a/source/gameengine/GameLogic/SCA_ANDController.h +++ b/source/gameengine/GameLogic/SCA_ANDController.h @@ -39,10 +39,18 @@ class SCA_ANDController : public SCA_IController Py_Header; //virtual void Trigger(class SCA_LogicManager* logicmgr); public: - SCA_ANDController(SCA_IObject* gameobj); + SCA_ANDController(SCA_IObject* gameobj,PyTypeObject* T=&Type); virtual ~SCA_ANDController(); virtual CValue* GetReplica(); virtual void Trigger(SCA_LogicManager* logicmgr); + + /* --------------------------------------------------------------------- */ + /* Python interface ---------------------------------------------------- */ + /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + }; #endif //__KX_ANDCONTROLLER diff --git a/source/gameengine/GameLogic/SCA_ActuatorSensor.cpp b/source/gameengine/GameLogic/SCA_ActuatorSensor.cpp index bdcc923e1d9..4dad65c5a25 100644 --- a/source/gameengine/GameLogic/SCA_ActuatorSensor.cpp +++ b/source/gameengine/GameLogic/SCA_ActuatorSensor.cpp @@ -40,8 +40,9 @@ SCA_ActuatorSensor::SCA_ActuatorSensor(SCA_EventManager* eventmgr, SCA_IObject* gameobj, - const STR_String& actname) - : SCA_ISensor(gameobj,eventmgr), + const STR_String& actname, + PyTypeObject* T ) + : SCA_ISensor(gameobj,eventmgr,T), m_checkactname(actname) { m_actuator = GetParent()->FindActuator(m_checkactname); @@ -137,15 +138,19 @@ PyTypeObject SCA_ActuatorSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_ActuatorSensor::Parents[] = { + &SCA_ActuatorSensor::Type, &SCA_ISensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_ActuatorSensor::Methods[] = { @@ -161,6 +166,18 @@ PyAttributeDef SCA_ActuatorSensor::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_ActuatorSensor::py_getattro(PyObject *attr) { + py_getattro_up(SCA_ISensor); +} + +PyObject* SCA_ActuatorSensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + +int SCA_ActuatorSensor::py_setattro(PyObject *attr, PyObject *value) { + py_setattro_up(SCA_ISensor); +} + int SCA_ActuatorSensor::CheckActuator(void *self, const PyAttributeDef*) { SCA_ActuatorSensor* sensor = reinterpret_cast<SCA_ActuatorSensor*>(self); @@ -180,7 +197,7 @@ const char SCA_ActuatorSensor::GetActuator_doc[] = PyObject* SCA_ActuatorSensor::PyGetActuator() { ShowDeprecationWarning("getActuator()", "the actuator property"); - return PyUnicode_FromString(m_checkactname); + return PyString_FromString(m_checkactname); } /* 4. setActuator */ diff --git a/source/gameengine/GameLogic/SCA_ActuatorSensor.h b/source/gameengine/GameLogic/SCA_ActuatorSensor.h index cf8e735cad4..6655e08dc70 100644 --- a/source/gameengine/GameLogic/SCA_ActuatorSensor.h +++ b/source/gameengine/GameLogic/SCA_ActuatorSensor.h @@ -46,7 +46,8 @@ class SCA_ActuatorSensor : public SCA_ISensor public: SCA_ActuatorSensor(class SCA_EventManager* eventmgr, SCA_IObject* gameobj, - const STR_String& actname); + const STR_String& actname, + PyTypeObject* T=&Type ); virtual ~SCA_ActuatorSensor(); virtual CValue* GetReplica(); @@ -60,6 +61,10 @@ public: /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + /* 3. setProperty */ KX_PYMETHOD_DOC_VARARGS(SCA_ActuatorSensor,SetActuator); /* 4. getProperty */ diff --git a/source/gameengine/GameLogic/SCA_AlwaysSensor.cpp b/source/gameengine/GameLogic/SCA_AlwaysSensor.cpp index ddb54c580b8..ff02680f191 100644 --- a/source/gameengine/GameLogic/SCA_AlwaysSensor.cpp +++ b/source/gameengine/GameLogic/SCA_AlwaysSensor.cpp @@ -48,8 +48,9 @@ /* ------------------------------------------------------------------------- */ SCA_AlwaysSensor::SCA_AlwaysSensor(class SCA_EventManager* eventmgr, - SCA_IObject* gameobj) - : SCA_ISensor(gameobj,eventmgr) + SCA_IObject* gameobj, + PyTypeObject* T) + : SCA_ISensor(gameobj,eventmgr, T) { //SetDrawColor(255,0,0); Init(); @@ -120,15 +121,19 @@ PyTypeObject SCA_AlwaysSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_AlwaysSensor::Parents[] = { + &SCA_AlwaysSensor::Type, &SCA_ISensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_AlwaysSensor::Methods[] = { @@ -139,4 +144,12 @@ PyAttributeDef SCA_AlwaysSensor::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_AlwaysSensor::py_getattro(PyObject *attr) { + py_getattro_up(SCA_ISensor); +} + +PyObject* SCA_AlwaysSensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + /* eof */ diff --git a/source/gameengine/GameLogic/SCA_AlwaysSensor.h b/source/gameengine/GameLogic/SCA_AlwaysSensor.h index d58e05564d1..0f85a641ef1 100644 --- a/source/gameengine/GameLogic/SCA_AlwaysSensor.h +++ b/source/gameengine/GameLogic/SCA_AlwaysSensor.h @@ -39,12 +39,22 @@ class SCA_AlwaysSensor : public SCA_ISensor bool m_alwaysresult; public: SCA_AlwaysSensor(class SCA_EventManager* eventmgr, - SCA_IObject* gameobj); + SCA_IObject* gameobj, + PyTypeObject* T =&Type); virtual ~SCA_AlwaysSensor(); virtual CValue* GetReplica(); virtual bool Evaluate(); virtual bool IsPositiveTrigger(); virtual void Init(); + + + /* --------------------------------------------------------------------- */ + /* Python interface ---------------------------------------------------- */ + /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + }; #endif //__KX_ALWAYSSENSOR diff --git a/source/gameengine/GameLogic/SCA_DelaySensor.cpp b/source/gameengine/GameLogic/SCA_DelaySensor.cpp index 11c6996a0a1..dcdae0b4e75 100644 --- a/source/gameengine/GameLogic/SCA_DelaySensor.cpp +++ b/source/gameengine/GameLogic/SCA_DelaySensor.cpp @@ -51,8 +51,9 @@ SCA_DelaySensor::SCA_DelaySensor(class SCA_EventManager* eventmgr, SCA_IObject* gameobj, int delay, int duration, - bool repeat) - : SCA_ISensor(gameobj,eventmgr), + bool repeat, + PyTypeObject* T) + : SCA_ISensor(gameobj,eventmgr, T), m_repeat(repeat), m_delay(delay), m_duration(duration) @@ -146,15 +147,19 @@ PyTypeObject SCA_DelaySensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_DelaySensor::Parents[] = { + &SCA_DelaySensor::Type, &SCA_ISensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_DelaySensor::Methods[] = { @@ -178,6 +183,19 @@ PyAttributeDef SCA_DelaySensor::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_DelaySensor::py_getattro(PyObject *attr) { + py_getattro_up(SCA_ISensor); +} + +PyObject* SCA_DelaySensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + +int SCA_DelaySensor::py_setattro(PyObject *attr, PyObject *value) { + py_setattro_up(SCA_ISensor); +} + + const char SCA_DelaySensor::SetDelay_doc[] = "setDelay(delay)\n" "\t- delay: length of the initial OFF period as number of frame\n" @@ -244,7 +262,7 @@ const char SCA_DelaySensor::GetDelay_doc[] = PyObject* SCA_DelaySensor::PyGetDelay() { ShowDeprecationWarning("getDelay()", "the delay property"); - return PyLong_FromSsize_t(m_delay); + return PyInt_FromLong(m_delay); } const char SCA_DelaySensor::GetDuration_doc[] = @@ -253,7 +271,7 @@ const char SCA_DelaySensor::GetDuration_doc[] = PyObject* SCA_DelaySensor::PyGetDuration() { ShowDeprecationWarning("getDuration()", "the duration property"); - return PyLong_FromSsize_t(m_duration); + return PyInt_FromLong(m_duration); } const char SCA_DelaySensor::GetRepeat_doc[] = diff --git a/source/gameengine/GameLogic/SCA_DelaySensor.h b/source/gameengine/GameLogic/SCA_DelaySensor.h index 8270e8959b7..5ccb33f8a16 100644 --- a/source/gameengine/GameLogic/SCA_DelaySensor.h +++ b/source/gameengine/GameLogic/SCA_DelaySensor.h @@ -47,7 +47,8 @@ public: SCA_IObject* gameobj, int delay, int duration, - bool repeat); + bool repeat, + PyTypeObject* T =&Type); virtual ~SCA_DelaySensor(); virtual CValue* GetReplica(); virtual bool Evaluate(); @@ -58,6 +59,10 @@ public: /* --------------------------------------------------------------------- */ /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); /* setProperty */ KX_PYMETHOD_DOC_VARARGS(SCA_DelaySensor,SetDelay); diff --git a/source/gameengine/GameLogic/SCA_ExpressionController.cpp b/source/gameengine/GameLogic/SCA_ExpressionController.cpp index 60969300474..8e044b89c71 100644 --- a/source/gameengine/GameLogic/SCA_ExpressionController.cpp +++ b/source/gameengine/GameLogic/SCA_ExpressionController.cpp @@ -46,8 +46,9 @@ /* ------------------------------------------------------------------------- */ SCA_ExpressionController::SCA_ExpressionController(SCA_IObject* gameobj, - const STR_String& exprtext) - :SCA_IController(gameobj), + const STR_String& exprtext, + PyTypeObject* T) + :SCA_IController(gameobj,T), m_exprText(exprtext), m_exprCache(NULL) { diff --git a/source/gameengine/GameLogic/SCA_ExpressionController.h b/source/gameengine/GameLogic/SCA_ExpressionController.h index 705f6dfc415..6a34d7b2dff 100644 --- a/source/gameengine/GameLogic/SCA_ExpressionController.h +++ b/source/gameengine/GameLogic/SCA_ExpressionController.h @@ -42,7 +42,8 @@ class SCA_ExpressionController : public SCA_IController public: SCA_ExpressionController(SCA_IObject* gameobj, - const STR_String& exprtext); + const STR_String& exprtext, + PyTypeObject* T=&Type ); virtual ~SCA_ExpressionController(); virtual CValue* GetReplica(); @@ -53,6 +54,14 @@ public: * so that self references are removed before the controller itself is released */ virtual void Delete(); + + /* --------------------------------------------------------------------- */ + /* Python interface ---------------------------------------------------- */ + /* --------------------------------------------------------------------- */ + +// virtual PyObject* py_getattro(PyObject *attr); +// virtual PyObject* py_getattro_dict(); + }; #endif //__KX_EXPRESSIONCONTROLLER diff --git a/source/gameengine/GameLogic/SCA_IActuator.cpp b/source/gameengine/GameLogic/SCA_IActuator.cpp index 0fda75590c1..be7c2651686 100644 --- a/source/gameengine/GameLogic/SCA_IActuator.cpp +++ b/source/gameengine/GameLogic/SCA_IActuator.cpp @@ -34,8 +34,9 @@ using namespace std; -SCA_IActuator::SCA_IActuator(SCA_IObject* gameobj) : - SCA_ILogicBrick(gameobj), +SCA_IActuator::SCA_IActuator(SCA_IObject* gameobj, + PyTypeObject* T) : + SCA_ILogicBrick(gameobj,T), m_links(0), m_posevent(false), m_negevent(false) diff --git a/source/gameengine/GameLogic/SCA_IActuator.h b/source/gameengine/GameLogic/SCA_IActuator.h index 13c718ee837..27afcbc386b 100644 --- a/source/gameengine/GameLogic/SCA_IActuator.h +++ b/source/gameengine/GameLogic/SCA_IActuator.h @@ -61,7 +61,8 @@ public: * This class also inherits the default copy constructors */ - SCA_IActuator(SCA_IObject* gameobj); + SCA_IActuator(SCA_IObject* gameobj, + PyTypeObject* T =&Type); /** * UnlinkObject(...) diff --git a/source/gameengine/GameLogic/SCA_IController.cpp b/source/gameengine/GameLogic/SCA_IController.cpp index 7cbb728753a..f2c3c83a2d9 100644 --- a/source/gameengine/GameLogic/SCA_IController.cpp +++ b/source/gameengine/GameLogic/SCA_IController.cpp @@ -37,9 +37,10 @@ #include <config.h> #endif -SCA_IController::SCA_IController(SCA_IObject* gameobj) +SCA_IController::SCA_IController(SCA_IObject* gameobj, + PyTypeObject* T) : - SCA_ILogicBrick(gameobj), + SCA_ILogicBrick(gameobj,T), m_statemask(0), m_justActivated(false) { @@ -215,15 +216,17 @@ PyTypeObject SCA_IController::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &SCA_ILogicBrick::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods +}; + +PyParentObject SCA_IController::Parents[] = { + &SCA_IController::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_IController::Methods[] = { @@ -245,6 +248,22 @@ PyAttributeDef SCA_IController::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_IController::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_ILogicBrick); +} + +PyObject* SCA_IController::py_getattro_dict() { + py_getattro_dict_up(SCA_ILogicBrick); +} + +int SCA_IController::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_ILogicBrick); +} + + + PyObject* SCA_IController::PyGetActuators() { ShowDeprecationWarning("getActuators()", "the actuators property"); @@ -262,7 +281,7 @@ PyObject* SCA_IController::PyGetSensor(PyObject* value) { ShowDeprecationWarning("getSensor(string)", "the sensors[string] property"); - char *scriptArg = _PyUnicode_AsString(value); + char *scriptArg = PyString_AsString(value); if (scriptArg==NULL) { PyErr_SetString(PyExc_TypeError, "controller.getSensor(string): Python Controller, expected a string (sensor name)"); return NULL; @@ -286,7 +305,7 @@ PyObject* SCA_IController::PyGetActuator(PyObject* value) { ShowDeprecationWarning("getActuator(string)", "the actuators[string] property"); - char *scriptArg = _PyUnicode_AsString(value); + char *scriptArg = PyString_AsString(value); if (scriptArg==NULL) { PyErr_SetString(PyExc_TypeError, "controller.getActuator(string): Python Controller, expected a string (actuator name)"); return NULL; @@ -321,13 +340,13 @@ PyObject* SCA_IController::PyGetSensors() PyObject* SCA_IController::PyGetState() { ShowDeprecationWarning("getState()", "the state property"); - return PyLong_FromSsize_t(m_statemask); + return PyInt_FromLong(m_statemask); } PyObject* SCA_IController::pyattr_get_state(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { SCA_IController* self= static_cast<SCA_IController*>(self_v); - return PyLong_FromSsize_t(self->m_statemask); + return PyInt_FromLong(self->m_statemask); } PyObject* SCA_IController::pyattr_get_sensors(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) diff --git a/source/gameengine/GameLogic/SCA_IController.h b/source/gameengine/GameLogic/SCA_IController.h index 523878bee26..a52c57ab3ed 100644 --- a/source/gameengine/GameLogic/SCA_IController.h +++ b/source/gameengine/GameLogic/SCA_IController.h @@ -47,7 +47,7 @@ protected: bool m_justActivated; bool m_bookmark; public: - SCA_IController(SCA_IObject* gameobj); + SCA_IController(SCA_IObject* gameobj,PyTypeObject* T); virtual ~SCA_IController(); virtual void Trigger(class SCA_LogicManager* logicmgr)=0; void LinkToSensor(SCA_ISensor* sensor); @@ -98,6 +98,10 @@ public: } } + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + KX_PYMETHOD_NOARGS(SCA_IController,GetSensors); KX_PYMETHOD_NOARGS(SCA_IController,GetActuators); KX_PYMETHOD_O(SCA_IController,GetSensor); diff --git a/source/gameengine/GameLogic/SCA_ILogicBrick.cpp b/source/gameengine/GameLogic/SCA_ILogicBrick.cpp index ccb79a2d49f..2dc80f54568 100644 --- a/source/gameengine/GameLogic/SCA_ILogicBrick.cpp +++ b/source/gameengine/GameLogic/SCA_ILogicBrick.cpp @@ -35,9 +35,10 @@ SCA_LogicManager* SCA_ILogicBrick::m_sCurrentLogicManager = NULL; -SCA_ILogicBrick::SCA_ILogicBrick(SCA_IObject* gameobj) +SCA_ILogicBrick::SCA_ILogicBrick(SCA_IObject* gameobj, + PyTypeObject* T) : - CValue(), + CValue(T), m_gameobj(gameobj), m_Execute_Priority(0), m_Execute_Ueber_Priority(0), @@ -193,17 +194,23 @@ PyTypeObject SCA_ILogicBrick::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + + +PyParentObject SCA_ILogicBrick::Parents[] = { + &SCA_ILogicBrick::Type, &CValue::Type, - 0,0,0,0,0,0, - py_base_new + NULL }; + + PyMethodDef SCA_ILogicBrick::Methods[] = { // --> Deprecated {"getOwner", (PyCFunction) SCA_ILogicBrick::sPyGetOwner, METH_NOARGS}, @@ -238,6 +245,21 @@ int SCA_ILogicBrick::CheckProperty(void *self, const PyAttributeDef *attrdef) return 0; } +PyObject* SCA_ILogicBrick::py_getattro(PyObject *attr) +{ + py_getattro_up(CValue); +} + +PyObject* SCA_ILogicBrick::py_getattro_dict() { + py_getattro_dict_up(CValue); +} + +int SCA_ILogicBrick::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(CValue); +} + + PyObject* SCA_ILogicBrick::PyGetOwner() { ShowDeprecationWarning("getOwner()", "the owner property"); @@ -274,7 +296,7 @@ PyObject* SCA_ILogicBrick::PySetExecutePriority(PyObject* args) PyObject* SCA_ILogicBrick::PyGetExecutePriority() { ShowDeprecationWarning("getExecutePriority()", "the executePriority property"); - return PyLong_FromSsize_t(m_Execute_Priority); + return PyInt_FromLong(m_Execute_Priority); } @@ -304,5 +326,5 @@ bool SCA_ILogicBrick::PyArgToBool(int boolArg) PyObject* SCA_ILogicBrick::BoolToPyArg(bool boolarg) { - return PyLong_FromSsize_t(boolarg? KX_TRUE: KX_FALSE); + return PyInt_FromLong(boolarg? KX_TRUE: KX_FALSE); } diff --git a/source/gameengine/GameLogic/SCA_ILogicBrick.h b/source/gameengine/GameLogic/SCA_ILogicBrick.h index 50679856802..779e5397a6a 100644 --- a/source/gameengine/GameLogic/SCA_ILogicBrick.h +++ b/source/gameengine/GameLogic/SCA_ILogicBrick.h @@ -53,7 +53,7 @@ protected: CValue* GetEvent(); public: - SCA_ILogicBrick(SCA_IObject* gameobj); + SCA_ILogicBrick(SCA_IObject* gameobj,PyTypeObject* T ); virtual ~SCA_ILogicBrick(); void SetExecutePriority(int execute_Priority); @@ -121,6 +121,10 @@ public: } virtual bool LessComparedTo(SCA_ILogicBrick* other); + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); static class SCA_LogicManager* m_sCurrentLogicManager; diff --git a/source/gameengine/GameLogic/SCA_IObject.cpp b/source/gameengine/GameLogic/SCA_IObject.cpp index 6cd11f9e553..9876f2512c0 100644 --- a/source/gameengine/GameLogic/SCA_IObject.cpp +++ b/source/gameengine/GameLogic/SCA_IObject.cpp @@ -41,11 +41,8 @@ MT_Point3 SCA_IObject::m_sDummy=MT_Point3(0,0,0); SG_QList SCA_IObject::m_activeBookmarkedControllers; -SCA_IObject::SCA_IObject(): - CValue(), - m_initState(0), - m_state(0), - m_firstState(NULL) +SCA_IObject::SCA_IObject(PyTypeObject* T): CValue(T), m_initState(0), m_state(0), m_firstState(NULL) + { m_suspended = false; } @@ -221,6 +218,51 @@ SCA_IActuator* SCA_IObject::FindActuator(const STR_String& actuatorname) } + +#if 0 +const MT_Point3& SCA_IObject::ConvertPythonPylist(PyObject* pylist) +{ + bool error = false; + m_sDummy = MT_Vector3(0,0,0); + if (pylist->ob_type == &CListValue::Type) + { + CListValue* listval = (CListValue*) pylist; + int numelem = listval->GetCount(); + if ( numelem <= 3) + { + int index; + for (index = 0;index<numelem;index++) + { + m_sDummy[index] = listval->GetValue(index)->GetNumber(); + } + } else + { + error = true; + } + + } else + { + + // assert the list is long enough... + int numitems = PyList_Size(pylist); + if (numitems <= 3) + { + int index; + for (index=0;index<numitems;index++) + { + m_sDummy[index] = PyFloat_AsDouble(PyList_GetItem(pylist,index)); + } + } + else + { + error = true; + } + + } + return m_sDummy; +} +#endif + void SCA_IObject::Suspend() { if ((!m_ignore_activity_culling) @@ -304,17 +346,23 @@ PyTypeObject SCA_IObject::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + + +PyParentObject SCA_IObject::Parents[] = { + &SCA_IObject::Type, &CValue::Type, - 0,0,0,0,0,0, - py_base_new + NULL }; + + PyMethodDef SCA_IObject::Methods[] = { //{"setOrientation", (PyCFunction) SCA_IObject::sPySetOrientation, METH_VARARGS}, //{"getOrientation", (PyCFunction) SCA_IObject::sPyGetOrientation, METH_VARARGS}, @@ -324,3 +372,12 @@ PyMethodDef SCA_IObject::Methods[] = { PyAttributeDef SCA_IObject::Attributes[] = { { NULL } //Sentinel }; + + +PyObject* SCA_IObject::py_getattro(PyObject *attr) { + py_getattro_up(CValue); +} + +PyObject* SCA_IObject::py_getattro_dict() { + py_getattro_dict_up(CValue); +} diff --git a/source/gameengine/GameLogic/SCA_IObject.h b/source/gameengine/GameLogic/SCA_IObject.h index 3060410dc6b..eae427741ca 100644 --- a/source/gameengine/GameLogic/SCA_IObject.h +++ b/source/gameengine/GameLogic/SCA_IObject.h @@ -105,7 +105,7 @@ protected: public: - SCA_IObject(); + SCA_IObject(PyTypeObject* T=&Type); virtual ~SCA_IObject(); SCA_ControllerList& GetControllers() @@ -199,12 +199,15 @@ public: unsigned int GetState(void) { return m_state; } // const class MT_Point3& ConvertPythonPylist(PyObject* pylist); + + // here come the python forwarded methods + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); virtual int GetGameObjectType() {return -1;} typedef enum ObjectTypes { OBJ_ARMATURE=0, - OBJ_CAMERA=1, }ObjectTypes; }; diff --git a/source/gameengine/GameLogic/SCA_ISensor.cpp b/source/gameengine/GameLogic/SCA_ISensor.cpp index 4c1e0bd01c4..2783bf14600 100644 --- a/source/gameengine/GameLogic/SCA_ISensor.cpp +++ b/source/gameengine/GameLogic/SCA_ISensor.cpp @@ -50,8 +50,9 @@ void SCA_ISensor::ReParent(SCA_IObject* parent) SCA_ISensor::SCA_ISensor(SCA_IObject* gameobj, - class SCA_EventManager* eventmgr) : - SCA_ILogicBrick(gameobj) + class SCA_EventManager* eventmgr, + PyTypeObject* T ) : + SCA_ILogicBrick(gameobj,T) { m_links = 0; m_suspended = false; @@ -300,7 +301,7 @@ PyObject* SCA_ISensor::PyIsPositive() { ShowDeprecationWarning("isPositive()", "the read-only positive property"); int retval = GetState(); - return PyLong_FromSsize_t(retval); + return PyInt_FromLong(retval); } const char SCA_ISensor::IsTriggered_doc[] = @@ -313,7 +314,7 @@ PyObject* SCA_ISensor::PyIsTriggered() int retval = 0; if (SCA_PythonController::m_sCurrentController) retval = SCA_PythonController::m_sCurrentController->IsTriggered(this); - return PyLong_FromSsize_t(retval); + return PyInt_FromLong(retval); } /** @@ -354,7 +355,7 @@ const char SCA_ISensor::GetFrequency_doc[] = PyObject* SCA_ISensor::PyGetFrequency() { ShowDeprecationWarning("getFrequency()", "the frequency property"); - return PyLong_FromSsize_t(m_pulse_frequency); + return PyInt_FromLong(m_pulse_frequency); } /** @@ -488,17 +489,19 @@ PyTypeObject SCA_ISensor::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &SCA_ILogicBrick::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods }; +PyParentObject SCA_ISensor::Parents[] = { + &SCA_ISensor::Type, + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL +}; PyMethodDef SCA_ISensor::Methods[] = { //Deprecated functions -----> {"isPositive", (PyCFunction) SCA_ISensor::sPyIsPositive, @@ -545,6 +548,19 @@ PyAttributeDef SCA_ISensor::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_ISensor::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_ILogicBrick); +} + +PyObject* SCA_ISensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ILogicBrick); +} + +int SCA_ISensor::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_ILogicBrick); +} PyObject* SCA_ISensor::pyattr_get_triggered(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { @@ -552,13 +568,13 @@ PyObject* SCA_ISensor::pyattr_get_triggered(void *self_v, const KX_PYATTRIBUTE_D int retval = 0; if (SCA_PythonController::m_sCurrentController) retval = SCA_PythonController::m_sCurrentController->IsTriggered(self); - return PyLong_FromSsize_t(retval); + return PyInt_FromLong(retval); } PyObject* SCA_ISensor::pyattr_get_positive(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { SCA_ISensor* self= static_cast<SCA_ISensor*>(self_v); - return PyLong_FromSsize_t(self->GetState()); + return PyInt_FromLong(self->GetState()); } int SCA_ISensor::pyattr_check_level(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) diff --git a/source/gameengine/GameLogic/SCA_ISensor.h b/source/gameengine/GameLogic/SCA_ISensor.h index 81864ab6a34..9bbd6ed41e4 100644 --- a/source/gameengine/GameLogic/SCA_ISensor.h +++ b/source/gameengine/GameLogic/SCA_ISensor.h @@ -101,7 +101,8 @@ public: }; SCA_ISensor(SCA_IObject* gameobj, - class SCA_EventManager* eventmgr);; + class SCA_EventManager* eventmgr, + PyTypeObject* T );; ~SCA_ISensor(); virtual void ReParent(SCA_IObject* parent); @@ -172,6 +173,10 @@ public: { return !m_links; } /* Python functions: */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); //Deprecated functions -----> KX_PYMETHOD_DOC_NOARGS(SCA_ISensor,IsPositive); diff --git a/source/gameengine/GameLogic/SCA_JoystickSensor.cpp b/source/gameengine/GameLogic/SCA_JoystickSensor.cpp index f55921e648b..336529667d7 100644 --- a/source/gameengine/GameLogic/SCA_JoystickSensor.cpp +++ b/source/gameengine/GameLogic/SCA_JoystickSensor.cpp @@ -46,8 +46,9 @@ SCA_JoystickSensor::SCA_JoystickSensor(class SCA_JoystickManager* eventmgr, short int joymode, int axis, int axisf,int prec, int button, - int hat, int hatf, bool allevents) - :SCA_ISensor(gameobj,eventmgr), + int hat, int hatf, bool allevents, + PyTypeObject* T ) + :SCA_ISensor(gameobj,eventmgr,T), m_pJoystickMgr(eventmgr), m_axis(axis), m_axisf(axisf), @@ -268,17 +269,23 @@ PyTypeObject SCA_JoystickSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + +PyParentObject SCA_JoystickSensor::Parents[] = { + &SCA_JoystickSensor::Type, &SCA_ISensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; + PyMethodDef SCA_JoystickSensor::Methods[] = { //Deprecated functions ------> {"getIndex", (PyCFunction) SCA_JoystickSensor::sPyGetIndex, METH_NOARGS, (PY_METHODCHAR)GetIndex_doc}, @@ -321,6 +328,20 @@ PyAttributeDef SCA_JoystickSensor::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_JoystickSensor::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_ISensor); +} + +PyObject* SCA_JoystickSensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + +int SCA_JoystickSensor::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_ISensor); +} + /* get index ---------------------------------------------------------- */ const char SCA_JoystickSensor::GetIndex_doc[] = @@ -328,7 +349,7 @@ const char SCA_JoystickSensor::GetIndex_doc[] = "\tReturns the joystick index to use.\n"; PyObject* SCA_JoystickSensor::PyGetIndex( ) { ShowDeprecationWarning("getIndex()", "the index property"); - return PyLong_FromSsize_t(m_joyindex); + return PyInt_FromLong(m_joyindex); } @@ -338,7 +359,7 @@ const char SCA_JoystickSensor::SetIndex_doc[] = "\tSets the joystick index to use.\n"; PyObject* SCA_JoystickSensor::PySetIndex( PyObject* value ) { ShowDeprecationWarning("setIndex()", "the index property"); - int index = PyLong_AsSsize_t( value ); /* -1 on error, will raise an error in this case */ + int index = PyInt_AsLong( value ); /* -1 on error, will raise an error in this case */ if (index < 0 || index >= JOYINDEX_MAX) { PyErr_SetString(PyExc_ValueError, "joystick index out of range or not an int"); return NULL; @@ -389,7 +410,7 @@ PyObject* SCA_JoystickSensor::PyGetAxisValue( ) { PyObject *list= PyList_New(axis_index); while(axis_index--) { - PyList_SET_ITEM(list, axis_index, PyLong_FromSsize_t(joy->GetAxisPosition(axis_index))); + PyList_SET_ITEM(list, axis_index, PyInt_FromLong(joy->GetAxisPosition(axis_index))); } return list; @@ -402,7 +423,7 @@ const char SCA_JoystickSensor::GetThreshold_doc[] = "\tReturns the threshold of the axis.\n"; PyObject* SCA_JoystickSensor::PyGetThreshold( ) { ShowDeprecationWarning("getThreshold()", "the threshold property"); - return PyLong_FromSsize_t(m_precision); + return PyInt_FromLong(m_precision); } @@ -426,7 +447,7 @@ const char SCA_JoystickSensor::GetButton_doc[] = "\tReturns the current button this sensor is checking.\n"; PyObject* SCA_JoystickSensor::PyGetButton( ) { ShowDeprecationWarning("getButton()", "the button property"); - return PyLong_FromSsize_t(m_button); + return PyInt_FromLong(m_button); } /* set button -------------------------------------------------------- */ @@ -435,7 +456,7 @@ const char SCA_JoystickSensor::SetButton_doc[] = "\tSets the button the sensor reacts to.\n"; PyObject* SCA_JoystickSensor::PySetButton( PyObject* value ) { ShowDeprecationWarning("setButton()", "the button property"); - int button = PyLong_AsSsize_t(value); + int button = PyInt_AsLong(value); if(button==-1 && PyErr_Occurred()) { PyErr_SetString(PyExc_ValueError, "expected an int"); return NULL; @@ -466,7 +487,7 @@ PyObject* SCA_JoystickSensor::PyGetButtonActiveList( ) { if(joy) { for (i=0; i < joy->GetNumberOfButtons(); i++) { if (joy->aButtonPressIsPositive(i)) { - value = PyLong_FromSsize_t(i); + value = PyInt_FromLong(i); PyList_Append(ls, value); Py_DECREF(value); } @@ -528,7 +549,7 @@ PyObject* SCA_JoystickSensor::PyNumberOfAxes( ) { ShowDeprecationWarning("getNumAxes()", "the numAxis property"); SCA_Joystick *joy = m_pJoystickMgr->GetJoystickDevice(m_joyindex); // when the joystick is null their is 0 exis still. dumb but scripters should use isConnected() - return PyLong_FromSsize_t( joy ? joy->GetNumberOfAxes() : 0 ); + return PyInt_FromLong( joy ? joy->GetNumberOfAxes() : 0 ); } @@ -538,7 +559,7 @@ const char SCA_JoystickSensor::NumberOfButtons_doc[] = PyObject* SCA_JoystickSensor::PyNumberOfButtons( ) { ShowDeprecationWarning("getNumButtons()", "the numButtons property"); SCA_Joystick *joy = m_pJoystickMgr->GetJoystickDevice(m_joyindex); - return PyLong_FromSsize_t( joy ? joy->GetNumberOfButtons() : 0 ); + return PyInt_FromLong( joy ? joy->GetNumberOfButtons() : 0 ); } @@ -548,7 +569,7 @@ const char SCA_JoystickSensor::NumberOfHats_doc[] = PyObject* SCA_JoystickSensor::PyNumberOfHats( ) { ShowDeprecationWarning("getNumHats()", "the numHats property"); SCA_Joystick *joy = m_pJoystickMgr->GetJoystickDevice(m_joyindex); - return PyLong_FromSsize_t( joy ? joy->GetNumberOfHats() : 0 ); + return PyInt_FromLong( joy ? joy->GetNumberOfHats() : 0 ); } const char SCA_JoystickSensor::Connected_doc[] = @@ -570,7 +591,7 @@ PyObject* SCA_JoystickSensor::pyattr_get_axis_values(void *self_v, const KX_PYAT PyObject *list= PyList_New(axis_index); while(axis_index--) { - PyList_SET_ITEM(list, axis_index, PyLong_FromSsize_t(joy->GetAxisPosition(axis_index))); + PyList_SET_ITEM(list, axis_index, PyInt_FromLong(joy->GetAxisPosition(axis_index))); } return list; @@ -586,7 +607,7 @@ PyObject* SCA_JoystickSensor::pyattr_get_axis_single(void *self_v, const KX_PYAT return NULL; } - return PyLong_FromSsize_t(joy->GetAxisPosition(self->m_axis-1)); + return PyInt_FromLong(joy->GetAxisPosition(self->m_axis-1)); } PyObject* SCA_JoystickSensor::pyattr_get_hat_values(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) @@ -598,7 +619,7 @@ PyObject* SCA_JoystickSensor::pyattr_get_hat_values(void *self_v, const KX_PYATT PyObject *list= PyList_New(hat_index); while(hat_index--) { - PyList_SET_ITEM(list, hat_index, PyLong_FromSsize_t(joy->GetHat(hat_index))); + PyList_SET_ITEM(list, hat_index, PyInt_FromLong(joy->GetHat(hat_index))); } return list; @@ -609,28 +630,28 @@ PyObject* SCA_JoystickSensor::pyattr_get_hat_single(void *self_v, const KX_PYATT SCA_JoystickSensor* self= static_cast<SCA_JoystickSensor*>(self_v); SCA_Joystick *joy = self->m_pJoystickMgr->GetJoystickDevice(self->m_joyindex); - return PyLong_FromSsize_t(joy->GetHat(self->m_hat-1)); + return PyInt_FromLong(joy->GetHat(self->m_hat-1)); } PyObject* SCA_JoystickSensor::pyattr_get_num_axis(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { SCA_JoystickSensor* self= static_cast<SCA_JoystickSensor*>(self_v); SCA_Joystick *joy = self->m_pJoystickMgr->GetJoystickDevice(self->m_joyindex); - return PyLong_FromSsize_t( joy ? joy->GetNumberOfAxes() : 0 ); + return PyInt_FromLong( joy ? joy->GetNumberOfAxes() : 0 ); } PyObject* SCA_JoystickSensor::pyattr_get_num_buttons(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { SCA_JoystickSensor* self= static_cast<SCA_JoystickSensor*>(self_v); SCA_Joystick *joy = self->m_pJoystickMgr->GetJoystickDevice(self->m_joyindex); - return PyLong_FromSsize_t( joy ? joy->GetNumberOfButtons() : 0 ); + return PyInt_FromLong( joy ? joy->GetNumberOfButtons() : 0 ); } PyObject* SCA_JoystickSensor::pyattr_get_num_hats(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { SCA_JoystickSensor* self= static_cast<SCA_JoystickSensor*>(self_v); SCA_Joystick *joy = self->m_pJoystickMgr->GetJoystickDevice(self->m_joyindex); - return PyLong_FromSsize_t( joy ? joy->GetNumberOfHats() : 0 ); + return PyInt_FromLong( joy ? joy->GetNumberOfHats() : 0 ); } PyObject* SCA_JoystickSensor::pyattr_get_connected(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) diff --git a/source/gameengine/GameLogic/SCA_JoystickSensor.h b/source/gameengine/GameLogic/SCA_JoystickSensor.h index 32f8ce567d2..e6a1d2eef32 100644 --- a/source/gameengine/GameLogic/SCA_JoystickSensor.h +++ b/source/gameengine/GameLogic/SCA_JoystickSensor.h @@ -106,7 +106,8 @@ public: short int joymode, int axis, int axisf,int prec, int button, - int hat, int hatf, bool allevents); + int hat, int hatf, bool allevents, + PyTypeObject* T=&Type ); virtual ~SCA_JoystickSensor(); virtual CValue* GetReplica(); @@ -122,6 +123,10 @@ public: /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + /* Joystick Index */ KX_PYMETHOD_DOC_NOARGS(SCA_JoystickSensor,GetIndex); KX_PYMETHOD_DOC_O(SCA_JoystickSensor,SetIndex); diff --git a/source/gameengine/GameLogic/SCA_KeyboardSensor.cpp b/source/gameengine/GameLogic/SCA_KeyboardSensor.cpp index 999e34dfa36..f8ee8ed8b41 100644 --- a/source/gameengine/GameLogic/SCA_KeyboardSensor.cpp +++ b/source/gameengine/GameLogic/SCA_KeyboardSensor.cpp @@ -48,8 +48,9 @@ SCA_KeyboardSensor::SCA_KeyboardSensor(SCA_KeyboardManager* keybdmgr, bool bAllKeys, const STR_String& targetProp, const STR_String& toggleProp, - SCA_IObject* gameobj) - :SCA_ISensor(gameobj,keybdmgr), + SCA_IObject* gameobj, + PyTypeObject* T ) + :SCA_ISensor(gameobj,keybdmgr,T), m_pKeyboardMgr(keybdmgr), m_hotkey(hotkey), m_qual(qual), @@ -417,7 +418,7 @@ const char SCA_KeyboardSensor::GetKey_doc[] = PyObject* SCA_KeyboardSensor::PyGetKey() { ShowDeprecationWarning("getKey()", "the key property"); - return PyLong_FromSsize_t(m_hotkey); + return PyInt_FromLong(m_hotkey); } /** 2. SetKey: change the key to look at */ @@ -449,7 +450,7 @@ const char SCA_KeyboardSensor::GetHold1_doc[] = PyObject* SCA_KeyboardSensor::PyGetHold1() { ShowDeprecationWarning("getHold1()", "the hold1 property"); - return PyLong_FromSsize_t(m_qual); + return PyInt_FromLong(m_qual); } /** 4. SetHold1: change the first bucky bit */ @@ -481,7 +482,7 @@ const char SCA_KeyboardSensor::GetHold2_doc[] = PyObject* SCA_KeyboardSensor::PyGetHold2() { ShowDeprecationWarning("getHold2()", "the hold2 property"); - return PyLong_FromSsize_t(m_qual2); + return PyInt_FromLong(m_qual2); } /** 6. SetHold2: change the second bucky bit */ @@ -531,8 +532,8 @@ PyObject* SCA_KeyboardSensor::PyGetPressedKeys() || (inevent.m_status == SCA_InputEvent::KX_JUSTRELEASED)) { PyObject* keypair = PyList_New(2); - PyList_SET_ITEM(keypair,0,PyLong_FromSsize_t(i)); - PyList_SET_ITEM(keypair,1,PyLong_FromSsize_t(inevent.m_status)); + PyList_SET_ITEM(keypair,0,PyInt_FromLong(i)); + PyList_SET_ITEM(keypair,1,PyInt_FromLong(inevent.m_status)); PyList_SET_ITEM(resultlist,index,keypair); index++; @@ -571,8 +572,8 @@ PyObject* SCA_KeyboardSensor::PyGetCurrentlyPressedKeys() || (inevent.m_status == SCA_InputEvent::KX_JUSTACTIVATED)) { PyObject* keypair = PyList_New(2); - PyList_SET_ITEM(keypair,0,PyLong_FromSsize_t(i)); - PyList_SET_ITEM(keypair,1,PyLong_FromSsize_t(inevent.m_status)); + PyList_SET_ITEM(keypair,0,PyInt_FromLong(i)); + PyList_SET_ITEM(keypair,1,PyInt_FromLong(inevent.m_status)); PyList_SET_ITEM(resultlist,index,keypair); index++; @@ -591,12 +592,12 @@ KX_PYMETHODDEF_DOC_O(SCA_KeyboardSensor, getKeyStatus, "getKeyStatus(keycode)\n" "\tGet the given key's status (KX_NO_INPUTSTATUS, KX_JUSTACTIVATED, KX_ACTIVE or KX_JUSTRELEASED).\n") { - if (!PyLong_Check(value)) { + if (!PyInt_Check(value)) { PyErr_SetString(PyExc_ValueError, "sensor.getKeyStatus(int): Keyboard Sensor, expected an int"); return NULL; } - int keycode = PyLong_AsSsize_t(value); + int keycode = PyInt_AsLong(value); if ((keycode < SCA_IInputDevice::KX_BEGINKEY) || (keycode > SCA_IInputDevice::KX_ENDKEY)){ @@ -606,7 +607,7 @@ KX_PYMETHODDEF_DOC_O(SCA_KeyboardSensor, getKeyStatus, SCA_IInputDevice* inputdev = m_pKeyboardMgr->GetInputDevice(); const SCA_InputEvent & inevent = inputdev->GetEventValue((SCA_IInputDevice::KX_EnumInputs) keycode); - return PyLong_FromSsize_t(inevent.m_status); + return PyInt_FromLong(inevent.m_status); } /* ------------------------------------------------------------------------- */ @@ -630,15 +631,19 @@ PyTypeObject SCA_KeyboardSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_KeyboardSensor::Parents[] = { + &SCA_KeyboardSensor::Type, &SCA_ISensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_KeyboardSensor::Methods[] = { @@ -667,6 +672,20 @@ PyAttributeDef SCA_KeyboardSensor::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_KeyboardSensor::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_ISensor); +} + +PyObject* SCA_KeyboardSensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + +int SCA_KeyboardSensor::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_ISensor); +} + PyObject* SCA_KeyboardSensor::pyattr_get_events(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { @@ -682,8 +701,8 @@ PyObject* SCA_KeyboardSensor::pyattr_get_events(void *self_v, const KX_PYATTRIBU if (inevent.m_status != SCA_InputEvent::KX_NO_INPUTSTATUS) { PyObject* keypair = PyList_New(2); - PyList_SET_ITEM(keypair,0,PyLong_FromSsize_t(i)); - PyList_SET_ITEM(keypair,1,PyLong_FromSsize_t(inevent.m_status)); + PyList_SET_ITEM(keypair,0,PyInt_FromLong(i)); + PyList_SET_ITEM(keypair,1,PyInt_FromLong(inevent.m_status)); PyList_Append(resultlist,keypair); } } diff --git a/source/gameengine/GameLogic/SCA_KeyboardSensor.h b/source/gameengine/GameLogic/SCA_KeyboardSensor.h index 3185b386d41..033225cd9be 100644 --- a/source/gameengine/GameLogic/SCA_KeyboardSensor.h +++ b/source/gameengine/GameLogic/SCA_KeyboardSensor.h @@ -94,7 +94,8 @@ public: bool bAllKeys, const STR_String& targetProp, const STR_String& toggleProp, - SCA_IObject* gameobj); + SCA_IObject* gameobj, + PyTypeObject* T=&Type ); virtual ~SCA_KeyboardSensor(); virtual CValue* GetReplica(); virtual void Init(); @@ -109,6 +110,10 @@ public: /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + //Deprecated functions -----> /** 1. GetKey : check which key this sensor looks at */ KX_PYMETHOD_DOC_NOARGS(SCA_KeyboardSensor,GetKey); diff --git a/source/gameengine/GameLogic/SCA_LogicManager.cpp b/source/gameengine/GameLogic/SCA_LogicManager.cpp index b782c6dfb93..83271288154 100644 --- a/source/gameengine/GameLogic/SCA_LogicManager.cpp +++ b/source/gameengine/GameLogic/SCA_LogicManager.cpp @@ -307,7 +307,6 @@ void SCA_LogicManager::AddTriggeredController(SCA_IController* controller, SCA_I controller->Activate(m_triggeredControllerSet); // so that the controller knows which sensor has activited it // only needed for python controller - // Note that this is safe even if the controller is subclassed. if (controller->GetType() == &SCA_PythonController::Type) { SCA_PythonController* pythonController = (SCA_PythonController*)controller; diff --git a/source/gameengine/GameLogic/SCA_MouseSensor.cpp b/source/gameengine/GameLogic/SCA_MouseSensor.cpp index 49fa19dce38..c5e1c3c0441 100644 --- a/source/gameengine/GameLogic/SCA_MouseSensor.cpp +++ b/source/gameengine/GameLogic/SCA_MouseSensor.cpp @@ -49,8 +49,9 @@ SCA_MouseSensor::SCA_MouseSensor(SCA_MouseManager* eventmgr, int startx,int starty, short int mousemode, - SCA_IObject* gameobj) - : SCA_ISensor(gameobj,eventmgr), + SCA_IObject* gameobj, + PyTypeObject* T) + : SCA_ISensor(gameobj,eventmgr, T), m_pMouseMgr(eventmgr), m_x(startx), m_y(starty) @@ -253,7 +254,7 @@ const char SCA_MouseSensor::GetXPosition_doc[] = "\tpixels\n"; PyObject* SCA_MouseSensor::PyGetXPosition() { ShowDeprecationWarning("getXPosition()", "the position property"); - return PyLong_FromSsize_t(m_x); + return PyInt_FromLong(m_x); } /* get y position ---------------------------------------------------------- */ @@ -264,7 +265,7 @@ const char SCA_MouseSensor::GetYPosition_doc[] = "\tpixels\n"; PyObject* SCA_MouseSensor::PyGetYPosition() { ShowDeprecationWarning("getYPosition()", "the position property"); - return PyLong_FromSsize_t(m_y); + return PyInt_FromLong(m_y); } //<----- Deprecated @@ -272,9 +273,9 @@ KX_PYMETHODDEF_DOC_O(SCA_MouseSensor, getButtonStatus, "getButtonStatus(button)\n" "\tGet the given button's status (KX_INPUT_NONE, KX_INPUT_NONE, KX_INPUT_JUST_ACTIVATED, KX_INPUT_ACTIVE, KX_INPUT_JUST_RELEASED).\n") { - if (PyLong_Check(value)) + if (PyInt_Check(value)) { - int button = PyLong_AsSsize_t(value); + int button = PyInt_AsLong(value); if ((button < SCA_IInputDevice::KX_LEFTMOUSE) || (button > SCA_IInputDevice::KX_RIGHTMOUSE)){ @@ -284,7 +285,7 @@ KX_PYMETHODDEF_DOC_O(SCA_MouseSensor, getButtonStatus, SCA_IInputDevice* mousedev = m_pMouseMgr->GetInputDevice(); const SCA_InputEvent& event = mousedev->GetEventValue((SCA_IInputDevice::KX_EnumInputs) button); - return PyLong_FromSsize_t(event.m_status); + return PyInt_FromLong(event.m_status); } Py_RETURN_NONE; @@ -311,15 +312,19 @@ PyTypeObject SCA_MouseSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_MouseSensor::Parents[] = { + &SCA_MouseSensor::Type, &SCA_ISensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_MouseSensor::Methods[] = { @@ -337,4 +342,18 @@ PyAttributeDef SCA_MouseSensor::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_MouseSensor::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_ISensor); +} + +PyObject* SCA_MouseSensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + +int SCA_MouseSensor::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_ISensor); +} + /* eof */ diff --git a/source/gameengine/GameLogic/SCA_MouseSensor.h b/source/gameengine/GameLogic/SCA_MouseSensor.h index 47f0378bf69..6d6302b514a 100644 --- a/source/gameengine/GameLogic/SCA_MouseSensor.h +++ b/source/gameengine/GameLogic/SCA_MouseSensor.h @@ -92,7 +92,8 @@ class SCA_MouseSensor : public SCA_ISensor SCA_MouseSensor(class SCA_MouseManager* keybdmgr, int startx,int starty, short int mousemode, - SCA_IObject* gameobj); + SCA_IObject* gameobj, + PyTypeObject* T=&Type ); virtual ~SCA_MouseSensor(); virtual CValue* GetReplica(); @@ -108,6 +109,10 @@ class SCA_MouseSensor : public SCA_ISensor /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + //Deprecated functions -----> /* read x-coordinate */ KX_PYMETHOD_DOC_NOARGS(SCA_MouseSensor,GetXPosition); diff --git a/source/gameengine/GameLogic/SCA_NANDController.cpp b/source/gameengine/GameLogic/SCA_NANDController.cpp index c00e5d6e617..d27aea5e6f7 100644 --- a/source/gameengine/GameLogic/SCA_NANDController.cpp +++ b/source/gameengine/GameLogic/SCA_NANDController.cpp @@ -42,9 +42,10 @@ /* Native functions */ /* ------------------------------------------------------------------------- */ -SCA_NANDController::SCA_NANDController(SCA_IObject* gameobj) +SCA_NANDController::SCA_NANDController(SCA_IObject* gameobj, + PyTypeObject* T) : - SCA_IController(gameobj) + SCA_IController(gameobj,T) { } @@ -115,15 +116,19 @@ PyTypeObject SCA_NANDController::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_NANDController::Parents[] = { + &SCA_NANDController::Type, &SCA_IController::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_NANDController::Methods[] = { @@ -134,4 +139,12 @@ PyAttributeDef SCA_NANDController::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_NANDController::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IController); +} + +PyObject* SCA_NANDController::py_getattro_dict() { + py_getattro_dict_up(SCA_IController); +} + /* eof */ diff --git a/source/gameengine/GameLogic/SCA_NANDController.h b/source/gameengine/GameLogic/SCA_NANDController.h index 36a145e5f2b..0ae0ff19745 100644 --- a/source/gameengine/GameLogic/SCA_NANDController.h +++ b/source/gameengine/GameLogic/SCA_NANDController.h @@ -39,7 +39,7 @@ class SCA_NANDController : public SCA_IController Py_Header; //virtual void Trigger(class SCA_LogicManager* logicmgr); public: - SCA_NANDController(SCA_IObject* gameobj); + SCA_NANDController(SCA_IObject* gameobj,PyTypeObject* T=&Type); virtual ~SCA_NANDController(); virtual CValue* GetReplica(); virtual void Trigger(SCA_LogicManager* logicmgr); @@ -47,6 +47,10 @@ public: /* --------------------------------------------------------------------- */ /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + }; #endif //__KX_NANDCONTROLLER diff --git a/source/gameengine/GameLogic/SCA_NORController.cpp b/source/gameengine/GameLogic/SCA_NORController.cpp index 9762d44fd5d..6c9141636b2 100644 --- a/source/gameengine/GameLogic/SCA_NORController.cpp +++ b/source/gameengine/GameLogic/SCA_NORController.cpp @@ -42,9 +42,10 @@ /* Native functions */ /* ------------------------------------------------------------------------- */ -SCA_NORController::SCA_NORController(SCA_IObject* gameobj) +SCA_NORController::SCA_NORController(SCA_IObject* gameobj, + PyTypeObject* T) : - SCA_IController(gameobj) + SCA_IController(gameobj,T) { } @@ -115,15 +116,19 @@ PyTypeObject SCA_NORController::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_NORController::Parents[] = { + &SCA_NORController::Type, &SCA_IController::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_NORController::Methods[] = { @@ -134,4 +139,12 @@ PyAttributeDef SCA_NORController::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_NORController::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IController); +} + +PyObject* SCA_NORController::py_getattro_dict() { + py_getattro_dict_up(SCA_IController); +} + /* eof */ diff --git a/source/gameengine/GameLogic/SCA_NORController.h b/source/gameengine/GameLogic/SCA_NORController.h index b96232375d6..06cbb70a489 100644 --- a/source/gameengine/GameLogic/SCA_NORController.h +++ b/source/gameengine/GameLogic/SCA_NORController.h @@ -39,10 +39,18 @@ class SCA_NORController : public SCA_IController Py_Header; //virtual void Trigger(class SCA_LogicManager* logicmgr); public: - SCA_NORController(SCA_IObject* gameobj); + SCA_NORController(SCA_IObject* gameobj,PyTypeObject* T=&Type); virtual ~SCA_NORController(); virtual CValue* GetReplica(); virtual void Trigger(SCA_LogicManager* logicmgr); + + /* --------------------------------------------------------------------- */ + /* Python interface ---------------------------------------------------- */ + /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + }; #endif //__KX_NORCONTROLLER diff --git a/source/gameengine/GameLogic/SCA_ORController.cpp b/source/gameengine/GameLogic/SCA_ORController.cpp index a526dd8353c..42c0a67d657 100644 --- a/source/gameengine/GameLogic/SCA_ORController.cpp +++ b/source/gameengine/GameLogic/SCA_ORController.cpp @@ -42,8 +42,9 @@ /* Native functions */ /* ------------------------------------------------------------------------- */ -SCA_ORController::SCA_ORController(SCA_IObject* gameobj) - :SCA_IController(gameobj) +SCA_ORController::SCA_ORController(SCA_IObject* gameobj, + PyTypeObject* T) + :SCA_IController(gameobj, T) { } @@ -109,15 +110,19 @@ PyTypeObject SCA_ORController::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_ORController::Parents[] = { + &SCA_ORController::Type, &SCA_IController::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_ORController::Methods[] = { @@ -128,4 +133,13 @@ PyAttributeDef SCA_ORController::Attributes[] = { { NULL } //Sentinel }; + +PyObject* SCA_ORController::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IController); +} + +PyObject* SCA_ORController::py_getattro_dict() { + py_getattro_dict_up(SCA_IController); +} + /* eof */ diff --git a/source/gameengine/GameLogic/SCA_ORController.h b/source/gameengine/GameLogic/SCA_ORController.h index 09d31a85190..66f772c739e 100644 --- a/source/gameengine/GameLogic/SCA_ORController.h +++ b/source/gameengine/GameLogic/SCA_ORController.h @@ -39,11 +39,18 @@ class SCA_ORController : public SCA_IController Py_Header; //virtual void Trigger(class SCA_LogicManager* logicmgr); public: - SCA_ORController(SCA_IObject* gameobj); + SCA_ORController(SCA_IObject* gameobj, PyTypeObject* T=&Type); virtual ~SCA_ORController(); virtual CValue* GetReplica(); virtual void Trigger(SCA_LogicManager* logicmgr); + + /* --------------------------------------------------------------------- */ + /* Python interface ---------------------------------------------------- */ + /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); }; #endif //__KX_ORCONTROLLER diff --git a/source/gameengine/GameLogic/SCA_PropertyActuator.cpp b/source/gameengine/GameLogic/SCA_PropertyActuator.cpp index 215e30eceaf..4faa4b55d4a 100644 --- a/source/gameengine/GameLogic/SCA_PropertyActuator.cpp +++ b/source/gameengine/GameLogic/SCA_PropertyActuator.cpp @@ -42,8 +42,8 @@ /* Native functions */ /* ------------------------------------------------------------------------- */ -SCA_PropertyActuator::SCA_PropertyActuator(SCA_IObject* gameobj,SCA_IObject* sourceObj,const STR_String& propname,const STR_String& expr,int acttype) - : SCA_IActuator(gameobj), +SCA_PropertyActuator::SCA_PropertyActuator(SCA_IObject* gameobj,SCA_IObject* sourceObj,const STR_String& propname,const STR_String& expr,int acttype,PyTypeObject* T ) + : SCA_IActuator(gameobj,T), m_type(acttype), m_propname(propname), m_exprtxt(expr), @@ -244,15 +244,19 @@ PyTypeObject SCA_PropertyActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_PropertyActuator::Parents[] = { + &SCA_PropertyActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_PropertyActuator::Methods[] = { @@ -272,6 +276,18 @@ PyAttributeDef SCA_PropertyActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_PropertyActuator::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IActuator); +} + +PyObject* SCA_PropertyActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int SCA_PropertyActuator::py_setattro(PyObject *attr, PyObject *value) { + py_setattro_up(SCA_IActuator); +} + /* 1. setProperty */ const char SCA_PropertyActuator::SetProperty_doc[] = "setProperty(name)\n" @@ -306,7 +322,7 @@ const char SCA_PropertyActuator::GetProperty_doc[] = PyObject* SCA_PropertyActuator::PyGetProperty(PyObject* args, PyObject* kwds) { ShowDeprecationWarning("getProperty()", "the 'propName' property"); - return PyUnicode_FromString(m_propname); + return PyString_FromString(m_propname); } /* 3. setValue */ @@ -336,7 +352,7 @@ const char SCA_PropertyActuator::GetValue_doc[] = PyObject* SCA_PropertyActuator::PyGetValue(PyObject* args, PyObject* kwds) { ShowDeprecationWarning("getValue()", "the value property"); - return PyUnicode_FromString(m_exprtxt); + return PyString_FromString(m_exprtxt); } /* eof */ diff --git a/source/gameengine/GameLogic/SCA_PropertyActuator.h b/source/gameengine/GameLogic/SCA_PropertyActuator.h index 8fb2e7a7bc5..a8df08dfc6e 100644 --- a/source/gameengine/GameLogic/SCA_PropertyActuator.h +++ b/source/gameengine/GameLogic/SCA_PropertyActuator.h @@ -64,7 +64,9 @@ public: SCA_IObject* sourceObj, const STR_String& propname, const STR_String& expr, - int acttype); + int acttype, + PyTypeObject* T=&Type + ); ~SCA_PropertyActuator(); @@ -84,6 +86,10 @@ public: /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + // python wrapped methods KX_PYMETHOD_DOC(SCA_PropertyActuator,SetProperty); KX_PYMETHOD_DOC(SCA_PropertyActuator,GetProperty); diff --git a/source/gameengine/GameLogic/SCA_PropertySensor.cpp b/source/gameengine/GameLogic/SCA_PropertySensor.cpp index 6d2e1a0aca5..3b343af3cba 100644 --- a/source/gameengine/GameLogic/SCA_PropertySensor.cpp +++ b/source/gameengine/GameLogic/SCA_PropertySensor.cpp @@ -48,8 +48,9 @@ SCA_PropertySensor::SCA_PropertySensor(SCA_EventManager* eventmgr, const STR_String& propname, const STR_String& propval, const STR_String& propmaxval, - KX_PROPSENSOR_TYPE checktype) - : SCA_ISensor(gameobj,eventmgr), + KX_PROPSENSOR_TYPE checktype, + PyTypeObject* T ) + : SCA_ISensor(gameobj,eventmgr,T), m_checktype(checktype), m_checkpropval(propval), m_checkpropmaxval(propmaxval), @@ -318,15 +319,19 @@ PyTypeObject SCA_PropertySensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_PropertySensor::Parents[] = { + &SCA_PropertySensor::Type, &SCA_ISensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_PropertySensor::Methods[] = { @@ -348,6 +353,19 @@ PyAttributeDef SCA_PropertySensor::Attributes[] = { { NULL } //Sentinel }; + +PyObject* SCA_PropertySensor::py_getattro(PyObject *attr) { + py_getattro_up(SCA_ISensor); +} + +PyObject* SCA_PropertySensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + +int SCA_PropertySensor::py_setattro(PyObject *attr, PyObject *value) { + py_setattro_up(SCA_ISensor); +} + /* 1. getType */ const char SCA_PropertySensor::GetType_doc[] = "getType()\n" @@ -355,7 +373,7 @@ const char SCA_PropertySensor::GetType_doc[] = PyObject* SCA_PropertySensor::PyGetType() { ShowDeprecationWarning("getType()", "the mode property"); - return PyLong_FromSsize_t(m_checktype); + return PyInt_FromLong(m_checktype); } /* 2. setType */ @@ -389,7 +407,7 @@ const char SCA_PropertySensor::GetProperty_doc[] = PyObject* SCA_PropertySensor::PyGetProperty() { ShowDeprecationWarning("getProperty()", "the 'propName' property"); - return PyUnicode_FromString(m_checkpropname); + return PyString_FromString(m_checkpropname); } /* 4. setProperty */ @@ -426,7 +444,7 @@ const char SCA_PropertySensor::GetValue_doc[] = PyObject* SCA_PropertySensor::PyGetValue() { ShowDeprecationWarning("getValue()", "the value property"); - return PyUnicode_FromString(m_checkpropval); + return PyString_FromString(m_checkpropval); } /* 6. setValue */ diff --git a/source/gameengine/GameLogic/SCA_PropertySensor.h b/source/gameengine/GameLogic/SCA_PropertySensor.h index 3513fcdf5ae..538ecd65949 100644 --- a/source/gameengine/GameLogic/SCA_PropertySensor.h +++ b/source/gameengine/GameLogic/SCA_PropertySensor.h @@ -67,7 +67,8 @@ public: const STR_String& propname, const STR_String& propval, const STR_String& propmaxval, - KX_PROPSENSOR_TYPE checktype); + KX_PROPSENSOR_TYPE checktype, + PyTypeObject* T=&Type ); /** * For property sensor, it is used to release the pre-calculated expression @@ -88,6 +89,10 @@ public: /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + /* 1. getType */ KX_PYMETHOD_DOC_NOARGS(SCA_PropertySensor,GetType); /* 2. setType */ diff --git a/source/gameengine/GameLogic/SCA_PythonController.cpp b/source/gameengine/GameLogic/SCA_PythonController.cpp index ffd95f00699..80e4f54c9c5 100644 --- a/source/gameengine/GameLogic/SCA_PythonController.cpp +++ b/source/gameengine/GameLogic/SCA_PythonController.cpp @@ -47,8 +47,10 @@ SCA_PythonController* SCA_PythonController::m_sCurrentController = NULL; -SCA_PythonController::SCA_PythonController(SCA_IObject* gameobj, int mode) - : SCA_IController(gameobj), +SCA_PythonController::SCA_PythonController(SCA_IObject* gameobj, + int mode, + PyTypeObject* T) + : SCA_IController(gameobj, T), m_bytecode(NULL), m_function(NULL), m_function_argc(0), @@ -148,7 +150,7 @@ void SCA_PythonController::SetDictionary(PyObject* pythondictionary) /* Without __file__ set the sys.argv[0] is used for the filename * which ends up with lines from the blender binary being printed in the console */ - PyDict_SetItemString(m_pythondictionary, "__file__", PyUnicode_FromString(m_scriptName.Ptr())); + PyDict_SetItemString(m_pythondictionary, "__file__", PyString_FromString(m_scriptName.Ptr())); } @@ -178,16 +180,16 @@ SCA_IActuator* SCA_PythonController::LinkedActuatorFromPy(PyObject *value) std::vector<SCA_IActuator*> lacts = m_sCurrentController->GetLinkedActuators(); std::vector<SCA_IActuator*>::iterator it; - if (PyUnicode_Check(value)) { + if (PyString_Check(value)) { /* get the actuator from the name */ - char *name= _PyUnicode_AsString(value); + char *name= PyString_AsString(value); for(it = lacts.begin(); it!= lacts.end(); ++it) { if( name == (*it)->GetName() ) { return *it; } } } - else if (PyObject_TypeCheck(value, &SCA_IActuator::Type)) { + else if (BGE_PROXY_CHECK_TYPE(value)) { PyObjectPlus *value_plus= BGE_PROXY_REF(value); for(it = lacts.begin(); it!= lacts.end(); ++it) { if( static_cast<SCA_IActuator*>(value_plus) == (*it) ) { @@ -198,7 +200,7 @@ SCA_IActuator* SCA_PythonController::LinkedActuatorFromPy(PyObject *value) /* set the exception */ PyObject *value_str = PyObject_Repr(value); /* new ref */ - PyErr_Format(PyExc_ValueError, "'%s' not in this python controllers actuator list", _PyUnicode_AsString(value_str)); + PyErr_Format(PyExc_ValueError, "'%s' not in this python controllers actuator list", PyString_AsString(value_str)); Py_DECREF(value_str); return false; @@ -243,17 +245,19 @@ PyTypeObject SCA_PythonController::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &SCA_IController::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods }; +PyParentObject SCA_PythonController::Parents[] = { + &SCA_PythonController::Type, + &SCA_IController::Type, + &CValue::Type, + NULL +}; PyMethodDef SCA_PythonController::Methods[] = { {"activate", (PyCFunction) SCA_PythonController::sPyActivate, METH_O}, {"deactivate", (PyCFunction) SCA_PythonController::sPyDeActivate, METH_O}, @@ -486,6 +490,22 @@ void SCA_PythonController::Trigger(SCA_LogicManager* logicmgr) m_sCurrentController = NULL; } + + +PyObject* SCA_PythonController::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IController); +} + +PyObject* SCA_PythonController::py_getattro_dict() { + py_getattro_dict_up(SCA_IController); +} + +int SCA_PythonController::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_IController); +} + PyObject* SCA_PythonController::PyActivate(PyObject *value) { if(m_sCurrentController != this) { @@ -520,13 +540,13 @@ PyObject* SCA_PythonController::PyDeActivate(PyObject *value) PyObject* SCA_PythonController::PyGetScript() { ShowDeprecationWarning("getScript()", "the script property"); - return PyUnicode_FromString(m_scriptText); + return PyString_FromString(m_scriptText); } /* 2. setScript */ PyObject* SCA_PythonController::PySetScript(PyObject* value) { - char *scriptArg = _PyUnicode_AsString(value); + char *scriptArg = PyString_AsString(value); ShowDeprecationWarning("setScript()", "the script property"); @@ -545,20 +565,15 @@ PyObject* SCA_PythonController::PySetScript(PyObject* value) PyObject* SCA_PythonController::pyattr_get_script(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { - //SCA_PythonController* self= static_cast<SCA_PythonController*>(static_cast<SCA_IController*>(static_cast<SCA_ILogicBrick*>(static_cast<CValue*>(static_cast<PyObjectPlus*>(self_v))))); - // static_cast<void *>(dynamic_cast<Derived *>(obj)) - static_cast<void *>(obj) - SCA_PythonController* self= static_cast<SCA_PythonController*>(self_v); - return PyUnicode_FromString(self->m_scriptText); + return PyString_FromString(self->m_scriptText); } - - int SCA_PythonController::pyattr_set_script(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) { SCA_PythonController* self= static_cast<SCA_PythonController*>(self_v); - char *scriptArg = _PyUnicode_AsString(value); + char *scriptArg = PyString_AsString(value); if (scriptArg==NULL) { PyErr_SetString(PyExc_TypeError, "controller.script = string: Python Controller, expected a string script text"); diff --git a/source/gameengine/GameLogic/SCA_PythonController.h b/source/gameengine/GameLogic/SCA_PythonController.h index 9311b3f355e..0c2af79c3a3 100644 --- a/source/gameengine/GameLogic/SCA_PythonController.h +++ b/source/gameengine/GameLogic/SCA_PythonController.h @@ -72,7 +72,7 @@ class SCA_PythonController : public SCA_IController //virtual CValue* AddRef(); //virtual int Release(); // Release a reference to this value (when reference count reaches 0, the value is removed from the heap) - SCA_PythonController(SCA_IObject* gameobj, int mode); + SCA_PythonController(SCA_IObject* gameobj, int mode, PyTypeObject* T = &Type); virtual ~SCA_PythonController(); virtual CValue* GetReplica(); @@ -96,6 +96,10 @@ class SCA_PythonController : public SCA_IController static PyObject* sPyAddActiveActuator(PyObject* self, PyObject* args); static SCA_IActuator* LinkedActuatorFromPy(PyObject *value); + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); KX_PYMETHOD_O(SCA_PythonController,Activate); diff --git a/source/gameengine/GameLogic/SCA_RandomActuator.cpp b/source/gameengine/GameLogic/SCA_RandomActuator.cpp index e903d10f9a5..a722590dd10 100644 --- a/source/gameengine/GameLogic/SCA_RandomActuator.cpp +++ b/source/gameengine/GameLogic/SCA_RandomActuator.cpp @@ -50,8 +50,9 @@ SCA_RandomActuator::SCA_RandomActuator(SCA_IObject *gameobj, SCA_RandomActuator::KX_RANDOMACT_MODE mode, float para1, float para2, - const STR_String &propName) - : SCA_IActuator(gameobj), + const STR_String &propName, + PyTypeObject* T) + : SCA_IActuator(gameobj, T), m_propname(propName), m_parameter1(para1), m_parameter2(para2), @@ -331,15 +332,19 @@ PyTypeObject SCA_RandomActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_RandomActuator::Parents[] = { + &SCA_RandomActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_RandomActuator::Methods[] = { @@ -379,14 +384,14 @@ PyAttributeDef SCA_RandomActuator::Attributes[] = { PyObject* SCA_RandomActuator::pyattr_get_seed(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef) { SCA_RandomActuator* act = static_cast<SCA_RandomActuator*>(self); - return PyLong_FromSsize_t(act->m_base->GetSeed()); + return PyInt_FromLong(act->m_base->GetSeed()); } int SCA_RandomActuator::pyattr_set_seed(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) { SCA_RandomActuator* act = static_cast<SCA_RandomActuator*>(self); - if (PyLong_Check(value)) { - int ival = PyLong_AsSsize_t(value); + if (PyInt_Check(value)) { + int ival = PyInt_AsLong(value); act->m_base->SetSeed(ival); return PY_SET_ATTR_SUCCESS; } else { @@ -395,6 +400,19 @@ int SCA_RandomActuator::pyattr_set_seed(void *self, const struct KX_PYATTRIBUTE_ } } +PyObject* SCA_RandomActuator::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IActuator); +} + +PyObject* SCA_RandomActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int SCA_RandomActuator::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_IActuator); +} + /* 1. setSeed */ const char SCA_RandomActuator::SetSeed_doc[] = "setSeed(seed)\n" @@ -421,7 +439,7 @@ const char SCA_RandomActuator::GetSeed_doc[] = PyObject* SCA_RandomActuator::PyGetSeed() { ShowDeprecationWarning("getSeed()", "the seed property"); - return PyLong_FromSsize_t(m_base->GetSeed()); + return PyInt_FromLong(m_base->GetSeed()); } /* 4. getPara1 */ @@ -455,7 +473,7 @@ const char SCA_RandomActuator::GetDistribution_doc[] = PyObject* SCA_RandomActuator::PyGetDistribution() { ShowDeprecationWarning("getDistribution()", "the distribution property"); - return PyLong_FromSsize_t(m_distribution); + return PyInt_FromLong(m_distribution); } /* 9. setProperty */ @@ -490,7 +508,7 @@ const char SCA_RandomActuator::GetProperty_doc[] = PyObject* SCA_RandomActuator::PyGetProperty() { ShowDeprecationWarning("getProperty()", "the 'propName' property"); - return PyUnicode_FromString(m_propname); + return PyString_FromString(m_propname); } /* 11. setBoolConst */ diff --git a/source/gameengine/GameLogic/SCA_RandomActuator.h b/source/gameengine/GameLogic/SCA_RandomActuator.h index c7d3fe21217..59863589b60 100644 --- a/source/gameengine/GameLogic/SCA_RandomActuator.h +++ b/source/gameengine/GameLogic/SCA_RandomActuator.h @@ -85,7 +85,8 @@ class SCA_RandomActuator : public SCA_IActuator KX_RANDOMACT_MODE mode, float para1, float para2, - const STR_String &propName); + const STR_String &propName, + PyTypeObject* T=&Type); virtual ~SCA_RandomActuator(); virtual bool Update(); @@ -96,6 +97,10 @@ class SCA_RandomActuator : public SCA_IActuator /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + static PyObject* pyattr_get_seed(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef); static int pyattr_set_seed(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value); diff --git a/source/gameengine/GameLogic/SCA_RandomSensor.cpp b/source/gameengine/GameLogic/SCA_RandomSensor.cpp index e036a77707e..d5cbeef01ae 100644 --- a/source/gameengine/GameLogic/SCA_RandomSensor.cpp +++ b/source/gameengine/GameLogic/SCA_RandomSensor.cpp @@ -46,8 +46,9 @@ SCA_RandomSensor::SCA_RandomSensor(SCA_EventManager* eventmgr, SCA_IObject* gameobj, - int startseed) - : SCA_ISensor(gameobj,eventmgr) + int startseed, + PyTypeObject* T) + : SCA_ISensor(gameobj,eventmgr, T) { m_basegenerator = new SCA_RandomNumberGenerator(startseed); Init(); @@ -146,15 +147,19 @@ PyTypeObject SCA_RandomSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_RandomSensor::Parents[] = { + &SCA_RandomSensor::Type, &SCA_ISensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_RandomSensor::Methods[] = { @@ -172,6 +177,19 @@ PyAttributeDef SCA_RandomSensor::Attributes[] = { {NULL} //Sentinel }; +PyObject* SCA_RandomSensor::py_getattro(PyObject *attr) { + py_getattro_up(SCA_ISensor); +} + +PyObject* SCA_RandomSensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + +int SCA_RandomSensor::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_ISensor); +} + /* 1. setSeed */ const char SCA_RandomSensor::SetSeed_doc[] = "setSeed(seed)\n" @@ -198,7 +216,7 @@ const char SCA_RandomSensor::GetSeed_doc[] = "\tequal series.\n"; PyObject* SCA_RandomSensor::PyGetSeed() { ShowDeprecationWarning("getSeed()", "the seed property"); - return PyLong_FromSsize_t(m_basegenerator->GetSeed()); + return PyInt_FromLong(m_basegenerator->GetSeed()); } /* 3. getLastDraw */ @@ -207,24 +225,24 @@ const char SCA_RandomSensor::GetLastDraw_doc[] = "\tReturn the last value that was drawn.\n"; PyObject* SCA_RandomSensor::PyGetLastDraw() { ShowDeprecationWarning("getLastDraw()", "the lastDraw property"); - return PyLong_FromSsize_t(m_lastdraw); + return PyInt_FromLong(m_lastdraw); } PyObject* SCA_RandomSensor::pyattr_get_seed(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { SCA_RandomSensor* self= static_cast<SCA_RandomSensor*>(self_v); - return PyLong_FromSsize_t(self->m_basegenerator->GetSeed()); + return PyInt_FromLong(self->m_basegenerator->GetSeed()); } int SCA_RandomSensor::pyattr_set_seed(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) { SCA_RandomSensor* self= static_cast<SCA_RandomSensor*>(self_v); - if (!PyLong_Check(value)) { + if (!PyInt_Check(value)) { PyErr_SetString(PyExc_TypeError, "sensor.seed = int: Random Sensor, expected an integer"); return PY_SET_ATTR_FAIL; } - self->m_basegenerator->SetSeed(PyLong_AsSsize_t(value)); + self->m_basegenerator->SetSeed(PyInt_AsLong(value)); return PY_SET_ATTR_SUCCESS; } diff --git a/source/gameengine/GameLogic/SCA_RandomSensor.h b/source/gameengine/GameLogic/SCA_RandomSensor.h index 5e66c36cccf..b2bf2440966 100644 --- a/source/gameengine/GameLogic/SCA_RandomSensor.h +++ b/source/gameengine/GameLogic/SCA_RandomSensor.h @@ -48,7 +48,8 @@ class SCA_RandomSensor : public SCA_ISensor public: SCA_RandomSensor(class SCA_EventManager* rndmgr, SCA_IObject* gameobj, - int startseed); + int startseed, + PyTypeObject* T=&Type); virtual ~SCA_RandomSensor(); virtual CValue* GetReplica(); virtual void ProcessReplica(); @@ -60,6 +61,10 @@ public: /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + /* 1. setSeed */ KX_PYMETHOD_DOC_VARARGS(SCA_RandomSensor,SetSeed); /* 2. getSeed */ diff --git a/source/gameengine/GameLogic/SCA_XNORController.cpp b/source/gameengine/GameLogic/SCA_XNORController.cpp index 527adc70cc6..aee8e26c21a 100644 --- a/source/gameengine/GameLogic/SCA_XNORController.cpp +++ b/source/gameengine/GameLogic/SCA_XNORController.cpp @@ -42,9 +42,10 @@ /* Native functions */ /* ------------------------------------------------------------------------- */ -SCA_XNORController::SCA_XNORController(SCA_IObject* gameobj) +SCA_XNORController::SCA_XNORController(SCA_IObject* gameobj, + PyTypeObject* T) : - SCA_IController(gameobj) + SCA_IController(gameobj,T) { } @@ -119,15 +120,19 @@ PyTypeObject SCA_XNORController::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_XNORController::Parents[] = { + &SCA_XNORController::Type, &SCA_IController::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_XNORController::Methods[] = { @@ -138,4 +143,12 @@ PyAttributeDef SCA_XNORController::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_XNORController::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IController); +} + +PyObject* SCA_XNORController::py_getattro_dict() { + py_getattro_dict_up(SCA_IController); +} + /* eof */ diff --git a/source/gameengine/GameLogic/SCA_XNORController.h b/source/gameengine/GameLogic/SCA_XNORController.h index 18e77fae665..4aad5763cb0 100644 --- a/source/gameengine/GameLogic/SCA_XNORController.h +++ b/source/gameengine/GameLogic/SCA_XNORController.h @@ -39,7 +39,7 @@ class SCA_XNORController : public SCA_IController Py_Header; //virtual void Trigger(class SCA_LogicManager* logicmgr); public: - SCA_XNORController(SCA_IObject* gameobj); + SCA_XNORController(SCA_IObject* gameobj,PyTypeObject* T=&Type); virtual ~SCA_XNORController(); virtual CValue* GetReplica(); virtual void Trigger(SCA_LogicManager* logicmgr); @@ -48,6 +48,9 @@ public: /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + }; #endif //__KX_XNORCONTROLLER diff --git a/source/gameengine/GameLogic/SCA_XORController.cpp b/source/gameengine/GameLogic/SCA_XORController.cpp index c0916224fe6..5afb3a750f5 100644 --- a/source/gameengine/GameLogic/SCA_XORController.cpp +++ b/source/gameengine/GameLogic/SCA_XORController.cpp @@ -42,9 +42,10 @@ /* Native functions */ /* ------------------------------------------------------------------------- */ -SCA_XORController::SCA_XORController(SCA_IObject* gameobj) +SCA_XORController::SCA_XORController(SCA_IObject* gameobj, + PyTypeObject* T) : - SCA_IController(gameobj) + SCA_IController(gameobj,T) { } @@ -119,15 +120,19 @@ PyTypeObject SCA_XORController::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject SCA_XORController::Parents[] = { + &SCA_XORController::Type, &SCA_IController::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef SCA_XORController::Methods[] = { @@ -138,4 +143,12 @@ PyAttributeDef SCA_XORController::Attributes[] = { { NULL } //Sentinel }; +PyObject* SCA_XORController::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IController); +} + +PyObject* SCA_XORController::py_getattro_dict() { + py_getattro_dict_up(SCA_IController); +} + /* eof */ diff --git a/source/gameengine/GameLogic/SCA_XORController.h b/source/gameengine/GameLogic/SCA_XORController.h index 2607a533661..feb9f2ed07c 100644 --- a/source/gameengine/GameLogic/SCA_XORController.h +++ b/source/gameengine/GameLogic/SCA_XORController.h @@ -39,10 +39,18 @@ class SCA_XORController : public SCA_IController Py_Header; //virtual void Trigger(class SCA_LogicManager* logicmgr); public: - SCA_XORController(SCA_IObject* gameobj); + SCA_XORController(SCA_IObject* gameobj,PyTypeObject* T=&Type); virtual ~SCA_XORController(); virtual CValue* GetReplica(); virtual void Trigger(SCA_LogicManager* logicmgr); + + /* --------------------------------------------------------------------- */ + /* Python interface ---------------------------------------------------- */ + /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + }; #endif //__KX_XORCONTROLLER diff --git a/source/gameengine/GamePlayer/common/Makefile b/source/gameengine/GamePlayer/common/Makefile index 4a952856739..84b4a4170a9 100644 --- a/source/gameengine/GamePlayer/common/Makefile +++ b/source/gameengine/GamePlayer/common/Makefile @@ -50,6 +50,8 @@ CPPFLAGS += -I$(NAN_GUARDEDALLOC)/include CPPFLAGS += -I$(NAN_FUZZICS)/include CPPFLAGS += -I$(NAN_STRING)/include CPPFLAGS += -I$(NAN_MOTO)/include +CPPFLAGS += -I$(NAN_SUMO)/include +CPPFLAGS += -I$(NAN_SOLID)/include CPPFLAGS += -I$(NAN_PNG)/include CPPFLAGS += -I$(NAN_ZLIB)/include CPPFLAGS += -I$(NAN_PYTHON)/include/python$(NAN_PYTHON_VERSION) @@ -67,6 +69,7 @@ CPPFLAGS += -I../../../gameengine/Network/LoopBackNetwork CPPFLAGS += -I../../../gameengine/Rasterizer CPPFLAGS += -I../../../gameengine/SceneGraph CPPFLAGS += -I../../../gameengine/Rasterizer/RAS_OpenGLRasterizer +CPPFLAGS += -I../../../gameengine/Physics/Sumo CPPFLAGS += -I../../../gameengine/Physics/common ############################### diff --git a/source/gameengine/GamePlayer/common/SConscript b/source/gameengine/GamePlayer/common/SConscript index f899385c841..e96b2c5400b 100644 --- a/source/gameengine/GamePlayer/common/SConscript +++ b/source/gameengine/GamePlayer/common/SConscript @@ -59,6 +59,11 @@ incs = ['.', # 'unix/GPU_System.cpp'] # gp_common_env.Append ( CPPPATH = ['unix']) +if env['WITH_BF_SOLID']: + incs.append('#source/gameengine/Physics/Sumo') + incs.append('#source/gameengine/Physics/Sumo/Fuzzics/include') + incs += Split(env['BF_SOLID_INC']) + incs += Split(env['BF_PYTHON_INC']) incs += Split(env['BF_PNG_INC']) incs += Split(env['BF_ZLIB_INC']) diff --git a/source/gameengine/GamePlayer/common/unix/GPU_Engine.cpp b/source/gameengine/GamePlayer/common/unix/GPU_Engine.cpp index 0ef087efbfe..a5dec02c753 100644 --- a/source/gameengine/GamePlayer/common/unix/GPU_Engine.cpp +++ b/source/gameengine/GamePlayer/common/unix/GPU_Engine.cpp @@ -44,6 +44,9 @@ #include "NG_LoopBackNetworkDeviceInterface.h" #include "SND_DeviceManager.h" #include "KX_BlenderSceneConverter.h" +#ifdef USE_SUMO_SOLID + #include "SM_Scene.h" +#endif #include "KX_KetsjiEngine.h" #include "GPC_RenderTools.h" diff --git a/source/gameengine/GamePlayer/common/unix/Makefile b/source/gameengine/GamePlayer/common/unix/Makefile index 08c52ddc904..90342c7b735 100644 --- a/source/gameengine/GamePlayer/common/unix/Makefile +++ b/source/gameengine/GamePlayer/common/unix/Makefile @@ -57,8 +57,10 @@ CPPFLAGS += -I../../../../gameengine/Rasterizer/RAS_OpenGLRasterizer CPPFLAGS += -I../../../../gameengine/SceneGraph CPPFLAGS += -I$(NAN_FUZZICS)/include +CPPFLAGS += -I$(NAN_SUMO)/include CPPFLAGS += -I$(NAN_SOUNDSYSTEM)/include CPPFLAGS += -I$(NAN_MOTO)/include +CPPFLAGS += -I$(NAN_SOLID)/include # Blender stuff CPPFLAGS += -I../../../../blender/blenkernel diff --git a/source/gameengine/GamePlayer/ghost/SConscript b/source/gameengine/GamePlayer/ghost/SConscript index 19234cb663c..390b6f5e089 100644 --- a/source/gameengine/GamePlayer/ghost/SConscript +++ b/source/gameengine/GamePlayer/ghost/SConscript @@ -41,6 +41,10 @@ incs = ['.', '#source/blender/gpu', '#extern/glew/include'] +if env['WITH_BF_SOLID']: + incs.append(['#source/gameengine/Physics/Sumo', '#source/gameengine/Physics/Sumo/Fuzzics/include']) + incs += Split(env['BF_SOLID_INC']) + incs += Split(env['BF_PYTHON_INC']) cxxflags = [] diff --git a/source/gameengine/Ketsji/BL_Shader.cpp b/source/gameengine/Ketsji/BL_Shader.cpp index 8bde5dd3a51..c5c517c8a65 100644 --- a/source/gameengine/Ketsji/BL_Shader.cpp +++ b/source/gameengine/Ketsji/BL_Shader.cpp @@ -113,8 +113,8 @@ bool BL_Shader::Ok()const return (mShader !=0 && mOk && mUse); } -BL_Shader::BL_Shader() -: PyObjectPlus(), +BL_Shader::BL_Shader(PyTypeObject *T) +: PyObjectPlus(T), mShader(0), mPass(1), mOk(0), @@ -728,6 +728,17 @@ void BL_Shader::SetUniform(int uniform, const int* val, int len) } } + +PyObject* BL_Shader::py_getattro(PyObject *attr) +{ + py_getattro_up(PyObjectPlus); +} + +PyObject* BL_Shader::py_getattro_dict() { + py_getattro_dict_up(PyObjectPlus); +} + + PyMethodDef BL_Shader::Methods[] = { // creation @@ -781,17 +792,21 @@ PyTypeObject BL_Shader::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &PyObjectPlus::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods }; + +PyParentObject BL_Shader::Parents[] = { + &BL_Shader::Type, + &PyObjectPlus::Type, + NULL +}; + + KX_PYMETHODDEF_DOC( BL_Shader, setSource," setSource(vertexProgram, fragmentProgram)" ) { if(mShader !=0 && mOk ) @@ -833,17 +848,17 @@ KX_PYMETHODDEF_DOC( BL_Shader, delSource, "delSource( )" ) KX_PYMETHODDEF_DOC( BL_Shader, isValid, "isValid()" ) { - return PyLong_FromSsize_t( ( mShader !=0 && mOk ) ); + return PyInt_FromLong( ( mShader !=0 && mOk ) ); } KX_PYMETHODDEF_DOC( BL_Shader, getVertexProg ,"getVertexProg( )" ) { - return PyUnicode_FromString(vertProg?vertProg:""); + return PyString_FromString(vertProg?vertProg:""); } KX_PYMETHODDEF_DOC( BL_Shader, getFragmentProg ,"getFragmentProg( )" ) { - return PyUnicode_FromString(fragProg?fragProg:""); + return PyString_FromString(fragProg?fragProg:""); } KX_PYMETHODDEF_DOC( BL_Shader, validate, "validate()") @@ -1208,7 +1223,7 @@ KX_PYMETHODDEF_DOC( BL_Shader, setUniformiv, "setUniformiv( uniform_name, (list2 for(unsigned int i=0; (i<list_size && i<4); i++) { PyObject *item = PySequence_GetItem(listPtr, i); - array_data[i] = PyLong_AsSsize_t(item); + array_data[i] = PyInt_AsLong(item); Py_DECREF(item); } diff --git a/source/gameengine/Ketsji/BL_Shader.h b/source/gameengine/Ketsji/BL_Shader.h index 42969996b3e..7db40e778ae 100644 --- a/source/gameengine/Ketsji/BL_Shader.h +++ b/source/gameengine/Ketsji/BL_Shader.h @@ -120,7 +120,7 @@ private: void ClearUniforms(); public: - BL_Shader(); + BL_Shader(PyTypeObject *T=&Type); virtual ~BL_Shader(); // Unused for now tangent is set as @@ -202,7 +202,9 @@ public: void SetUniform(int uniform, const int val); // Python interface - virtual PyObject* py_repr(void) { return PyUnicode_FromFormat("BL_Shader\n\tvertex shader:%s\n\n\tfragment shader%s\n\n", vertProg, fragProg); } + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual PyObject* py_repr(void) { return PyString_FromFormat("BL_Shader\n\tvertex shader:%s\n\n\tfragment shader%s\n\n", vertProg, fragProg); } // ----------------------------------- KX_PYMETHOD_DOC( BL_Shader, setSource ); diff --git a/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageActuator.cpp b/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageActuator.cpp index 7cb287d02b2..63773352d96 100644 --- a/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageActuator.cpp +++ b/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageActuator.cpp @@ -41,8 +41,9 @@ KX_NetworkMessageActuator::KX_NetworkMessageActuator( const STR_String &toPropName, const STR_String &subject, int bodyType, - const STR_String &body) : - SCA_IActuator(gameobj), + const STR_String &body, + PyTypeObject* T) : + SCA_IActuator(gameobj,T), m_networkscene(networkscene), m_toPropName(toPropName), m_subject(subject), @@ -117,15 +118,19 @@ PyTypeObject KX_NetworkMessageActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_NetworkMessageActuator::Parents[] = { + &KX_NetworkMessageActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_NetworkMessageActuator::Methods[] = { @@ -150,6 +155,18 @@ PyAttributeDef KX_NetworkMessageActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_NetworkMessageActuator::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_NetworkMessageActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_NetworkMessageActuator::py_setattro(PyObject *attr, PyObject *value) { + py_setattro_up(SCA_IActuator); +} + // Deprecated -----> // 1. SetToPropName PyObject* KX_NetworkMessageActuator::PySetToPropName( @@ -223,4 +240,4 @@ PyObject* KX_NetworkMessageActuator::PySetBody( Py_RETURN_NONE; } -// <----- Deprecated +// <----- Deprecated
\ No newline at end of file diff --git a/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageActuator.h b/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageActuator.h index b4f55f2a466..cf92fd46fe0 100644 --- a/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageActuator.h +++ b/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageActuator.h @@ -50,7 +50,8 @@ public: const STR_String &toPropName, const STR_String &subject, int bodyType, - const STR_String &body); + const STR_String &body, + PyTypeObject* T=&Type); virtual ~KX_NetworkMessageActuator(); virtual bool Update(); @@ -60,6 +61,10 @@ public: /* Python interface ------------------------------------------- */ /* ------------------------------------------------------------ */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + // Deprecated -----> KX_PYMETHOD(KX_NetworkMessageActuator, SetToPropName); KX_PYMETHOD(KX_NetworkMessageActuator, SetSubject); diff --git a/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.cpp b/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.cpp index 78dda1f6db7..8ddcd87b66f 100644 --- a/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.cpp +++ b/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.cpp @@ -50,9 +50,10 @@ KX_NetworkMessageSensor::KX_NetworkMessageSensor( class KX_NetworkEventManager* eventmgr, // our eventmanager class NG_NetworkScene *NetworkScene, // our scene SCA_IObject* gameobj, // the sensor controlling object - const STR_String &subject + const STR_String &subject, + PyTypeObject* T ) : - SCA_ISensor(gameobj,eventmgr), + SCA_ISensor(gameobj,eventmgr,T), m_Networkeventmgr(eventmgr), m_NetworkScene(NetworkScene), m_subject(subject), @@ -181,15 +182,19 @@ PyTypeObject KX_NetworkMessageSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_NetworkMessageSensor::Parents[] = { + &KX_NetworkMessageSensor::Type, &SCA_ISensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_NetworkMessageSensor::Methods[] = { @@ -221,6 +226,18 @@ PyAttributeDef KX_NetworkMessageSensor::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_NetworkMessageSensor::py_getattro(PyObject *attr) { + py_getattro_up(SCA_ISensor); +} + +PyObject* KX_NetworkMessageSensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + +int KX_NetworkMessageSensor::py_setattro(PyObject *attr, PyObject *value) { + return SCA_ISensor::py_setattro(attr, value); +} + PyObject* KX_NetworkMessageSensor::pyattr_get_bodies(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_NetworkMessageSensor *self = static_cast<KX_NetworkMessageSensor*>(self_v); @@ -250,7 +267,7 @@ const char KX_NetworkMessageSensor::SetSubjectFilterText_doc[] = PyObject* KX_NetworkMessageSensor::PySetSubjectFilterText(PyObject* value) { ShowDeprecationWarning("setSubjectFilterText()", "subject"); - char* Subject = _PyUnicode_AsString(value); + char* Subject = PyString_AsString(value); if (Subject==NULL) { PyErr_SetString(PyExc_TypeError, "sensor.tsetSubjectFilterText(string): KX_NetworkMessageSensor, expected a string message"); return NULL; @@ -268,7 +285,7 @@ const char KX_NetworkMessageSensor::GetFrameMessageCount_doc[] = PyObject* KX_NetworkMessageSensor::PyGetFrameMessageCount() { ShowDeprecationWarning("getFrameMessageCount()", "frameMessageCount"); - return PyLong_FromSsize_t(long(m_frame_message_count)); + return PyInt_FromLong(long(m_frame_message_count)); } // 3. Get the message bodies @@ -294,7 +311,7 @@ const char KX_NetworkMessageSensor::GetSubject_doc[] = PyObject* KX_NetworkMessageSensor::PyGetSubject() { ShowDeprecationWarning("getSubject()", "subject"); - return PyUnicode_FromString(m_subject ? m_subject : ""); + return PyString_FromString(m_subject ? m_subject : ""); } // 5. Get the message subjects @@ -311,4 +328,4 @@ PyObject* KX_NetworkMessageSensor::PyGetSubjects() return (new CListValue())->NewProxy(true); } } -// <----- Deprecated +// <----- Deprecated
\ No newline at end of file diff --git a/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.h b/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.h index ade87697303..53183f33826 100644 --- a/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.h +++ b/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.h @@ -57,7 +57,8 @@ public: KX_NetworkEventManager* eventmgr, // our eventmanager NG_NetworkScene *NetworkScene, // our scene SCA_IObject* gameobj, // the sensor controlling object - const STR_String &subject + const STR_String &subject, + PyTypeObject* T=&Type ); virtual ~KX_NetworkMessageSensor(); @@ -71,6 +72,10 @@ public: /* Python interface -------------------------------------------- */ /* ------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + // Deprecated -----> KX_PYMETHOD_DOC_O(KX_NetworkMessageSensor, SetSubjectFilterText); KX_PYMETHOD_DOC_NOARGS(KX_NetworkMessageSensor, GetFrameMessageCount); diff --git a/source/gameengine/Ketsji/KX_BlenderMaterial.cpp b/source/gameengine/Ketsji/KX_BlenderMaterial.cpp index 314becc702d..30057fc039d 100644 --- a/source/gameengine/Ketsji/KX_BlenderMaterial.cpp +++ b/source/gameengine/Ketsji/KX_BlenderMaterial.cpp @@ -42,8 +42,10 @@ BL_BlenderShader *KX_BlenderMaterial::mLastBlenderShader = NULL; //static PyObject *gTextureDict = 0; -KX_BlenderMaterial::KX_BlenderMaterial() -: PyObjectPlus(), +KX_BlenderMaterial::KX_BlenderMaterial( + PyTypeObject *T + ) +: PyObjectPlus(T), RAS_IPolyMaterial(), mMaterial(NULL), mShader(0), @@ -811,17 +813,36 @@ PyTypeObject KX_BlenderMaterial::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &PyObjectPlus::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods }; + +PyParentObject KX_BlenderMaterial::Parents[] = { + &KX_BlenderMaterial::Type, + &PyObjectPlus::Type, + NULL +}; + + +PyObject* KX_BlenderMaterial::py_getattro(PyObject *attr) +{ + py_getattro_up(PyObjectPlus); +} + +PyObject* KX_BlenderMaterial::py_getattro_dict() { + py_getattro_dict_up(PyObjectPlus); +} + +int KX_BlenderMaterial::py_setattro(PyObject *attr, PyObject *pyvalue) +{ + return PyObjectPlus::py_setattro(attr, pyvalue); +} + + KX_PYMETHODDEF_DOC( KX_BlenderMaterial, getShader , "getShader()") { if( !GLEW_ARB_fragment_shader) { @@ -891,7 +912,7 @@ void KX_BlenderMaterial::SetBlenderGLSLShader(int layer) KX_PYMETHODDEF_DOC( KX_BlenderMaterial, getMaterialIndex, "getMaterialIndex()") { - return PyLong_FromSsize_t( GetMaterialIndex() ); + return PyInt_FromLong( GetMaterialIndex() ); } KX_PYMETHODDEF_DOC( KX_BlenderMaterial, getTexture, "getTexture( index )" ) diff --git a/source/gameengine/Ketsji/KX_BlenderMaterial.h b/source/gameengine/Ketsji/KX_BlenderMaterial.h index 1f5edc1d7d1..b29f2df98db 100644 --- a/source/gameengine/Ketsji/KX_BlenderMaterial.h +++ b/source/gameengine/Ketsji/KX_BlenderMaterial.h @@ -23,7 +23,9 @@ class KX_BlenderMaterial : public PyObjectPlus, public RAS_IPolyMaterial Py_Header; public: // -------------------------------- - KX_BlenderMaterial(); + KX_BlenderMaterial( + PyTypeObject* T=&Type + ); void Initialize( class KX_Scene* scene, BL_Material* mat, @@ -81,7 +83,10 @@ public: ); // -------------------------------- - virtual PyObject* py_repr(void) { return PyUnicode_FromString(mMaterial->matname.ReadPtr()); } + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *pyvalue); + virtual PyObject* py_repr(void) { return PyString_FromString(mMaterial->matname.ReadPtr()); } KX_PYMETHOD_DOC( KX_BlenderMaterial, getShader ); KX_PYMETHOD_DOC( KX_BlenderMaterial, getMaterialIndex ); diff --git a/source/gameengine/Ketsji/KX_CDActuator.cpp b/source/gameengine/Ketsji/KX_CDActuator.cpp index bfca81f45d9..8511526fd5f 100644 --- a/source/gameengine/Ketsji/KX_CDActuator.cpp +++ b/source/gameengine/Ketsji/KX_CDActuator.cpp @@ -48,8 +48,9 @@ KX_CDActuator::KX_CDActuator(SCA_IObject* gameobject, KX_CDACT_TYPE type, int track, short start, - short end) - : SCA_IActuator(gameobject) + short end, + PyTypeObject* T) + : SCA_IActuator(gameobject,T) { m_soundscene = soundscene; m_type = type; @@ -170,17 +171,25 @@ PyTypeObject KX_CDActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + + +PyParentObject KX_CDActuator::Parents[] = { + &KX_CDActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; + + PyMethodDef KX_CDActuator::Methods[] = { // Deprecated -----> {"setGain",(PyCFunction) KX_CDActuator::sPySetGain,METH_VARARGS,NULL}, @@ -208,6 +217,22 @@ int KX_CDActuator::pyattr_setGain(void *self, const struct KX_PYATTRIBUTE_DEF *a return PY_SET_ATTR_SUCCESS; } +PyObject* KX_CDActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_CDActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_CDActuator::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_IActuator); +} + + + KX_PYMETHODDEF_DOC_NOARGS(KX_CDActuator, startCD, "startCD()\n" "\tStarts the CD playing.\n") @@ -248,8 +273,8 @@ KX_PYMETHODDEF_DOC_O(KX_CDActuator, playTrack, "playTrack(trackNumber)\n" "\tPlays the track selected.\n") { - if (PyLong_Check(value)) { - int track = PyLong_AsSsize_t(value); + if (PyInt_Check(value)) { + int track = PyInt_AsLong(value); SND_CDObject::Instance()->SetPlaymode(SND_CD_TRACK); SND_CDObject::Instance()->SetTrack(track); SND_CDObject::Instance()->SetPlaystate(SND_MUST_PLAY); diff --git a/source/gameengine/Ketsji/KX_CDActuator.h b/source/gameengine/Ketsji/KX_CDActuator.h index b01ad73777e..2fd05ab72e5 100644 --- a/source/gameengine/Ketsji/KX_CDActuator.h +++ b/source/gameengine/Ketsji/KX_CDActuator.h @@ -68,7 +68,8 @@ public: KX_CDACT_TYPE type, int track, short start, - short end); + short end, + PyTypeObject* T=&Type); ~KX_CDActuator(); @@ -80,6 +81,10 @@ public: /* Python interface --------------------------------------------------- */ /* -------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + // Deprecated -----> KX_PYMETHOD_VARARGS(KX_CDActuator,SetGain); KX_PYMETHOD_VARARGS(KX_CDActuator,GetGain); diff --git a/source/gameengine/Ketsji/KX_Camera.cpp b/source/gameengine/Ketsji/KX_Camera.cpp index f762699f780..40f6c99c03c 100644 --- a/source/gameengine/Ketsji/KX_Camera.cpp +++ b/source/gameengine/Ketsji/KX_Camera.cpp @@ -42,9 +42,10 @@ KX_Camera::KX_Camera(void* sgReplicationInfo, SG_Callbacks callbacks, const RAS_CameraData& camdata, bool frustum_culling, - bool delete_node) + bool delete_node, + PyTypeObject *T) : - KX_GameObject(sgReplicationInfo,callbacks), + KX_GameObject(sgReplicationInfo,callbacks,T), m_camdata(camdata), m_dirty(true), m_normalized(false), @@ -550,19 +551,41 @@ PyTypeObject KX_Camera::Type = { &KX_GameObject::Sequence, &KX_GameObject::Mapping, 0,0,0, - NULL, - NULL, + py_base_getattro, + py_base_setattro, 0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, + Py_TPFLAGS_DEFAULT, 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &KX_GameObject::Type, - 0,0,0,0,0,0, - py_base_new + Methods +}; + + + + + + +PyParentObject KX_Camera::Parents[] = { + &KX_Camera::Type, + &KX_GameObject::Type, + &SCA_IObject::Type, + &CValue::Type, + NULL }; +PyObject* KX_Camera::py_getattro(PyObject *attr) +{ + py_getattro_up(KX_GameObject); +} + +PyObject* KX_Camera::py_getattro_dict() { + py_getattro_dict_up(KX_GameObject); +} + +int KX_Camera::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(KX_GameObject); +} + KX_PYMETHODDEF_DOC_VARARGS(KX_Camera, sphereInsideFrustum, "sphereInsideFrustum(center, radius) -> Integer\n" "\treturns INSIDE, OUTSIDE or INTERSECT if the given sphere is\n" @@ -588,7 +611,7 @@ KX_PYMETHODDEF_DOC_VARARGS(KX_Camera, sphereInsideFrustum, MT_Point3 center; if (PyVecTo(pycenter, center)) { - return PyLong_FromSsize_t(SphereInsideFrustum(center, radius)); /* new ref */ + return PyInt_FromLong(SphereInsideFrustum(center, radius)); /* new ref */ } } @@ -639,7 +662,7 @@ KX_PYMETHODDEF_DOC_O(KX_Camera, boxInsideFrustum, return NULL; } - return PyLong_FromSsize_t(BoxInsideFrustum(box)); /* new ref */ + return PyInt_FromLong(BoxInsideFrustum(box)); /* new ref */ } KX_PYMETHODDEF_DOC_O(KX_Camera, pointInsideFrustum, @@ -661,7 +684,7 @@ KX_PYMETHODDEF_DOC_O(KX_Camera, pointInsideFrustum, MT_Point3 point; if (PyVecTo(value, point)) { - return PyLong_FromSsize_t(PointInsideFrustum(point)); /* new ref */ + return PyInt_FromLong(PointInsideFrustum(point)); /* new ref */ } PyErr_SetString(PyExc_TypeError, "camera.pointInsideFrustum(point): KX_Camera, expected point argument."); @@ -929,11 +952,11 @@ PyObject* KX_Camera::pyattr_get_world_to_camera(void *self_v, const KX_PYATTRIBU PyObject* KX_Camera::pyattr_get_INSIDE(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) -{ return PyLong_FromSsize_t(INSIDE); } +{ return PyInt_FromLong(INSIDE); } PyObject* KX_Camera::pyattr_get_OUTSIDE(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) -{ return PyLong_FromSsize_t(OUTSIDE); } +{ return PyInt_FromLong(OUTSIDE); } PyObject* KX_Camera::pyattr_get_INTERSECT(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) -{ return PyLong_FromSsize_t(INTERSECT); } +{ return PyInt_FromLong(INTERSECT); } bool ConvertPythonToCamera(PyObject * value, KX_Camera **object, bool py_none_ok, const char *error_prefix) @@ -955,14 +978,14 @@ bool ConvertPythonToCamera(PyObject * value, KX_Camera **object, bool py_none_ok } } - if (PyUnicode_Check(value)) { - STR_String value_str = _PyUnicode_AsString(value); + if (PyString_Check(value)) { + STR_String value_str = PyString_AsString(value); *object = KX_GetActiveScene()->FindCamera(value_str); if (*object) { return true; } else { - PyErr_Format(PyExc_ValueError, "%s, requested name \"%s\" did not match any KX_Camera in this scene", error_prefix, _PyUnicode_AsString(value)); + PyErr_Format(PyExc_ValueError, "%s, requested name \"%s\" did not match any KX_Camera in this scene", error_prefix, PyString_AsString(value)); return false; } } @@ -1119,7 +1142,7 @@ KX_PYMETHODDEF_DOC_VARARGS(KX_Camera, getScreenRay, PyTuple_SET_ITEM(argValue, 0, PyObjectFrom(vect)); PyTuple_SET_ITEM(argValue, 1, PyFloat_FromDouble(dist)); if (propName) - PyTuple_SET_ITEM(argValue, 2, PyUnicode_FromString(propName)); + PyTuple_SET_ITEM(argValue, 2, PyString_FromString(propName)); PyObject* ret= this->PyrayCastTo(argValue,NULL); Py_DECREF(argValue); diff --git a/source/gameengine/Ketsji/KX_Camera.h b/source/gameengine/Ketsji/KX_Camera.h index 74c8e6d4e4f..aef21cd91e4 100644 --- a/source/gameengine/Ketsji/KX_Camera.h +++ b/source/gameengine/Ketsji/KX_Camera.h @@ -143,7 +143,7 @@ public: enum { INSIDE, INTERSECT, OUTSIDE } ; - KX_Camera(void* sgReplicationInfo,SG_Callbacks callbacks,const RAS_CameraData& camdata, bool frustum_culling = true, bool delete_node = false); + KX_Camera(void* sgReplicationInfo,SG_Callbacks callbacks,const RAS_CameraData& camdata, bool frustum_culling = true, bool delete_node = false, PyTypeObject *T = &Type); virtual ~KX_Camera(); /** @@ -265,7 +265,6 @@ public: */ int GetViewportTop() const; - virtual int GetGameObjectType() { return OBJ_CAMERA; } KX_PYMETHOD_DOC_VARARGS(KX_Camera, sphereInsideFrustum); KX_PYMETHOD_DOC_O(KX_Camera, boxInsideFrustum); @@ -283,6 +282,10 @@ public: KX_PYMETHOD_DOC_O(KX_Camera, getScreenPosition); KX_PYMETHOD_DOC_VARARGS(KX_Camera, getScreenVect); KX_PYMETHOD_DOC_VARARGS(KX_Camera, getScreenRay); + + virtual PyObject* py_getattro(PyObject *attr); /* lens, near, far, projection_matrix */ + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *pyvalue); static PyObject* pyattr_get_perspective(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef); static int pyattr_set_perspective(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value); diff --git a/source/gameengine/Ketsji/KX_CameraActuator.cpp b/source/gameengine/Ketsji/KX_CameraActuator.cpp index 3d3b68ed85d..f8557dac2c4 100644 --- a/source/gameengine/Ketsji/KX_CameraActuator.cpp +++ b/source/gameengine/Ketsji/KX_CameraActuator.cpp @@ -56,9 +56,10 @@ KX_CameraActuator::KX_CameraActuator( float hght, float minhght, float maxhght, - bool xytog + bool xytog, + PyTypeObject* T ): - SCA_IActuator(gameobj), + SCA_IActuator(gameobj, T), m_ob (obj), m_height (hght), m_minHeight (minhght), @@ -384,15 +385,19 @@ PyTypeObject KX_CameraActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_CameraActuator::Parents[] = { + &KX_CameraActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_CameraActuator::Methods[] = { @@ -419,6 +424,18 @@ PyAttributeDef KX_CameraActuator::Attributes[] = { {NULL} }; +PyObject* KX_CameraActuator::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_CameraActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_CameraActuator::py_setattro(PyObject *attr, PyObject* value) { + py_setattro_up(SCA_IActuator); +} + /* get obj ---------------------------------------------------------- */ const char KX_CameraActuator::GetObject_doc[] = "getObject(name_only = 1)\n" @@ -437,7 +454,7 @@ PyObject* KX_CameraActuator::PyGetObject(PyObject* args) Py_RETURN_NONE; if (ret_name_only) - return PyUnicode_FromString(m_ob->GetName().ReadPtr()); + return PyString_FromString(m_ob->GetName().ReadPtr()); else return m_ob->GetProxy(); } @@ -562,7 +579,7 @@ const char KX_CameraActuator::GetXY_doc[] = PyObject* KX_CameraActuator::PyGetXY() { ShowDeprecationWarning("getXY()", "the xy property"); - return PyLong_FromSsize_t(m_x); + return PyInt_FromLong(m_x); } PyObject* KX_CameraActuator::pyattr_get_object(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) diff --git a/source/gameengine/Ketsji/KX_CameraActuator.h b/source/gameengine/Ketsji/KX_CameraActuator.h index 057c6fed770..efa4e2f38d7 100644 --- a/source/gameengine/Ketsji/KX_CameraActuator.h +++ b/source/gameengine/Ketsji/KX_CameraActuator.h @@ -91,7 +91,9 @@ private : float hght, float minhght, float maxhght, - bool xytog + bool xytog, + PyTypeObject* T=&Type + ); @@ -118,6 +120,10 @@ private : /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); + /* set object to look at */ KX_PYMETHOD_DOC_O(KX_CameraActuator,SetObject); /* get current object */ diff --git a/source/gameengine/Ketsji/KX_ClientObjectInfo.h b/source/gameengine/Ketsji/KX_ClientObjectInfo.h index 1898dc71ef8..077ac96f0ac 100644 --- a/source/gameengine/Ketsji/KX_ClientObjectInfo.h +++ b/source/gameengine/Ketsji/KX_ClientObjectInfo.h @@ -30,6 +30,9 @@ #define __KX_CLIENTOBJECT_INFO_H /* Note, the way this works with/without sumo is a bit odd */ +#ifdef USE_SUMO_SOLID +#include <SM_Object.h> +#endif //USE_SUMO_SOLID #include <list> @@ -39,6 +42,9 @@ class KX_GameObject; * Client Type and Additional Info. This structure can be use instead of a bare void* pointer, for safeness, and additional info for callbacks */ struct KX_ClientObjectInfo +#ifdef USE_SUMO_SOLID + : public SM_ClientObject +#endif { enum clienttype { STATIC, @@ -53,12 +59,18 @@ struct KX_ClientObjectInfo std::list<SCA_ISensor*> m_sensors; public: KX_ClientObjectInfo(KX_GameObject *gameobject, clienttype type = STATIC, void *auxilary_info = NULL) : +#ifdef USE_SUMO_SOLID + SM_ClientObject(), +#endif m_type(type), m_gameobject(gameobject), m_auxilary_info(auxilary_info) {} KX_ClientObjectInfo(const KX_ClientObjectInfo ©) : +#ifdef USE_SUMO_SOLID + SM_ClientObject(copy), +#endif m_type(copy.m_type), m_gameobject(copy.m_gameobject), m_auxilary_info(copy.m_auxilary_info) diff --git a/source/gameengine/Ketsji/KX_ConstraintActuator.cpp b/source/gameengine/Ketsji/KX_ConstraintActuator.cpp index d09eae647c8..bd03dea486b 100644 --- a/source/gameengine/Ketsji/KX_ConstraintActuator.cpp +++ b/source/gameengine/Ketsji/KX_ConstraintActuator.cpp @@ -54,8 +54,9 @@ KX_ConstraintActuator::KX_ConstraintActuator(SCA_IObject *gameobj, int locrotxyz, int time, int option, - char *property) : - SCA_IActuator(gameobj), + char *property, + PyTypeObject* T) : + SCA_IActuator(gameobj, T), m_refDirVector(refDir), m_currentTime(0) { @@ -580,15 +581,19 @@ PyTypeObject KX_ConstraintActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_ConstraintActuator::Parents[] = { + &KX_ConstraintActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_ConstraintActuator::Methods[] = { @@ -634,6 +639,21 @@ PyAttributeDef KX_ConstraintActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_ConstraintActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_ConstraintActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_ConstraintActuator::py_setattro(PyObject *attr, PyObject* value) +{ + py_setattro_up(SCA_IActuator); +} + + int KX_ConstraintActuator::pyattr_check_direction(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef) { KX_ConstraintActuator* act = static_cast<KX_ConstraintActuator*>(self); @@ -671,7 +691,7 @@ const char KX_ConstraintActuator::GetDamp_doc[] = "\tReturns the damping parameter.\n"; PyObject* KX_ConstraintActuator::PyGetDamp(){ ShowDeprecationWarning("getDamp()", "the damp property"); - return PyLong_FromSsize_t(m_posDampTime); + return PyInt_FromLong(m_posDampTime); } /* 2. setRotDamp */ @@ -698,7 +718,7 @@ const char KX_ConstraintActuator::GetRotDamp_doc[] = "\tReturns the damping time for application of the constraint.\n"; PyObject* KX_ConstraintActuator::PyGetRotDamp(){ ShowDeprecationWarning("getRotDamp()", "the rotDamp property"); - return PyLong_FromSsize_t(m_rotDampTime); + return PyInt_FromLong(m_rotDampTime); } /* 2. setDirection */ @@ -771,7 +791,7 @@ const char KX_ConstraintActuator::GetOption_doc[] = "\tReturns the option parameter.\n"; PyObject* KX_ConstraintActuator::PyGetOption(){ ShowDeprecationWarning("getOption()", "the option property"); - return PyLong_FromSsize_t(m_option); + return PyInt_FromLong(m_option); } /* 2. setTime */ @@ -800,7 +820,7 @@ const char KX_ConstraintActuator::GetTime_doc[] = "\tReturns the time parameter.\n"; PyObject* KX_ConstraintActuator::PyGetTime(){ ShowDeprecationWarning("getTime()", "the time property"); - return PyLong_FromSsize_t(m_activeTime); + return PyInt_FromLong(m_activeTime); } /* 2. setProperty */ @@ -829,7 +849,7 @@ const char KX_ConstraintActuator::GetProperty_doc[] = "\tReturns the property parameter.\n"; PyObject* KX_ConstraintActuator::PyGetProperty(){ ShowDeprecationWarning("getProperty()", "the 'property' property"); - return PyUnicode_FromString(m_property.Ptr()); + return PyString_FromString(m_property.Ptr()); } /* 4. setDistance */ @@ -958,7 +978,7 @@ const char KX_ConstraintActuator::GetLimit_doc[] = "\tReturns the type of constraint.\n"; PyObject* KX_ConstraintActuator::PyGetLimit() { ShowDeprecationWarning("setLimit()", "the limit property"); - return PyLong_FromSsize_t(m_locrot); + return PyInt_FromLong(m_locrot); } /* eof */ diff --git a/source/gameengine/Ketsji/KX_ConstraintActuator.h b/source/gameengine/Ketsji/KX_ConstraintActuator.h index 677904aedc9..40607b44947 100644 --- a/source/gameengine/Ketsji/KX_ConstraintActuator.h +++ b/source/gameengine/Ketsji/KX_ConstraintActuator.h @@ -126,7 +126,8 @@ protected: int locrot, int time, int option, - char *property); + char *property, + PyTypeObject* T=&Type); virtual ~KX_ConstraintActuator(); virtual CValue* GetReplica() { KX_ConstraintActuator* replica = new KX_ConstraintActuator(*this); @@ -140,6 +141,10 @@ protected: /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); + static int pyattr_check_direction(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef); static int pyattr_check_min(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef); diff --git a/source/gameengine/Ketsji/KX_ConstraintWrapper.cpp b/source/gameengine/Ketsji/KX_ConstraintWrapper.cpp index ec7bb470235..c5cf67af67d 100644 --- a/source/gameengine/Ketsji/KX_ConstraintWrapper.cpp +++ b/source/gameengine/Ketsji/KX_ConstraintWrapper.cpp @@ -38,8 +38,8 @@ KX_ConstraintWrapper::KX_ConstraintWrapper( PHY_ConstraintType ctype, int constraintId, - PHY_IPhysicsEnvironment* physenv) : - PyObjectPlus(), + PHY_IPhysicsEnvironment* physenv,PyTypeObject *T) : + PyObjectPlus(T), m_constraintId(constraintId), m_constraintType(ctype), m_physenv(physenv) @@ -51,7 +51,7 @@ KX_ConstraintWrapper::~KX_ConstraintWrapper() PyObject* KX_ConstraintWrapper::PyGetConstraintId() { - return PyLong_FromSsize_t(m_constraintId); + return PyInt_FromLong(m_constraintId); } @@ -99,17 +99,37 @@ PyTypeObject KX_ConstraintWrapper::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &PyObjectPlus::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods +}; + +PyParentObject KX_ConstraintWrapper::Parents[] = { + &KX_ConstraintWrapper::Type, + NULL +}; + +//here you can search for existing data members (like mass,friction etc.) +PyObject* KX_ConstraintWrapper::py_getattro(PyObject *attr) +{ + py_getattro_up(PyObjectPlus); +} + +PyObject* KX_ConstraintWrapper::py_getattro_dict() { + py_getattro_dict_up(PyObjectPlus); +} + +int KX_ConstraintWrapper::py_setattro(PyObject *attr,PyObject* value) +{ + py_setattro_up(PyObjectPlus); }; + + + + PyMethodDef KX_ConstraintWrapper::Methods[] = { {"getConstraintId",(PyCFunction) KX_ConstraintWrapper::sPyGetConstraintId, METH_NOARGS}, {"setParam",(PyCFunction) KX_ConstraintWrapper::sPySetParam, METH_VARARGS}, diff --git a/source/gameengine/Ketsji/KX_ConstraintWrapper.h b/source/gameengine/Ketsji/KX_ConstraintWrapper.h index 74670944415..03813e0f167 100644 --- a/source/gameengine/Ketsji/KX_ConstraintWrapper.h +++ b/source/gameengine/Ketsji/KX_ConstraintWrapper.h @@ -35,8 +35,11 @@ class KX_ConstraintWrapper : public PyObjectPlus { Py_Header; + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); public: - KX_ConstraintWrapper(PHY_ConstraintType ctype,int constraintId,class PHY_IPhysicsEnvironment* physenv); + KX_ConstraintWrapper(PHY_ConstraintType ctype,int constraintId,class PHY_IPhysicsEnvironment* physenv,PyTypeObject *T = &Type); virtual ~KX_ConstraintWrapper (); int getConstraintId() { return m_constraintId;}; diff --git a/source/gameengine/Ketsji/KX_ConvertPhysicsObject.h b/source/gameengine/Ketsji/KX_ConvertPhysicsObject.h index 9d3b9cdaf74..74042366bae 100644 --- a/source/gameengine/Ketsji/KX_ConvertPhysicsObject.h +++ b/source/gameengine/Ketsji/KX_ConvertPhysicsObject.h @@ -32,8 +32,11 @@ /* These are defined by the build system... */ //but the build system is broken, because it doesn't allow for 2 or more defines at once. //Please leave Sumo _AND_ Bullet enabled +//#define USE_SUMO_SOLID // scons defines this #define USE_BULLET +//#define USE_ODE + //on visual studio 7/8, always enable BULLET for now //you can have multiple physics engines running anyway, and //the scons build system doesn't really support this at the moment. @@ -145,6 +148,20 @@ struct KX_ObjectProperties } m_boundobject; }; +#ifdef USE_ODE + + +void KX_ConvertODEEngineObject(KX_GameObject* gameobj, + RAS_MeshObject* meshobj, + KX_Scene* kxscene, + struct PHY_ShapeProps* shapeprops, + struct PHY_MaterialProps* smmaterial, + struct KX_ObjectProperties* objprop); + + +#endif //USE_ODE + + void KX_ConvertDynamoObject(KX_GameObject* gameobj, RAS_MeshObject* meshobj, KX_Scene* kxscene, @@ -152,6 +169,19 @@ void KX_ConvertDynamoObject(KX_GameObject* gameobj, struct PHY_MaterialProps* smmaterial, struct KX_ObjectProperties* objprop); +#ifdef USE_SUMO_SOLID + +void KX_ConvertSumoObject( class KX_GameObject* gameobj, + class RAS_MeshObject* meshobj, + class KX_Scene* kxscene, + struct PHY_ShapeProps* shapeprops, + struct PHY_MaterialProps* smmaterial, + struct KX_ObjectProperties* objprop); + +void KX_ClearSumoSharedShapes(); +bool KX_ReInstanceShapeFromMesh(RAS_MeshObject* meshobj); + +#endif #ifdef USE_BULLET diff --git a/source/gameengine/Ketsji/KX_ConvertPhysicsObjects.cpp b/source/gameengine/Ketsji/KX_ConvertPhysicsObjects.cpp index 64b5760de28..51c41c0686d 100644 --- a/source/gameengine/Ketsji/KX_ConvertPhysicsObjects.cpp +++ b/source/gameengine/Ketsji/KX_ConvertPhysicsObjects.cpp @@ -32,6 +32,7 @@ #include "MT_assert.h" +// defines USE_ODE to choose physics engine #include "KX_ConvertPhysicsObject.h" #include "BL_DeformableGameObject.h" #include "RAS_MeshObject.h" @@ -55,6 +56,597 @@ extern "C"{ #include "BKE_DerivedMesh.h" } +#ifdef USE_ODE + +#include "KX_OdePhysicsController.h" +#include "OdePhysicsEnvironment.h" +#endif //USE_ODE + + +// USE_SUMO_SOLID is defined in headerfile KX_ConvertPhysicsObject.h +#ifdef USE_SUMO_SOLID + + +#include "SumoPhysicsEnvironment.h" +#include "KX_SumoPhysicsController.h" + + +// sumo physics specific +#include "SM_Object.h" +#include "SM_FhObject.h" +#include "SM_Scene.h" +#include "SM_ClientObjectInfo.h" + +#include "KX_SumoPhysicsController.h" + +struct KX_PhysicsInstance +{ + DT_VertexBaseHandle m_vertexbase; + RAS_DisplayArray* m_darray; + RAS_IPolyMaterial* m_material; + + KX_PhysicsInstance(DT_VertexBaseHandle vertex_base, RAS_DisplayArray *darray, RAS_IPolyMaterial* mat) + : m_vertexbase(vertex_base), + m_darray(darray), + m_material(mat) + { + } + + ~KX_PhysicsInstance() + { + DT_DeleteVertexBase(m_vertexbase); + } +}; + +static GEN_Map<GEN_HashedPtr,DT_ShapeHandle> map_gamemesh_to_sumoshape; +static GEN_Map<GEN_HashedPtr, KX_PhysicsInstance*> map_gamemesh_to_instance; + +// forward declarations +static void BL_RegisterSumoObject(KX_GameObject* gameobj,class SM_Scene* sumoScene,class SM_Object* sumoObj,const STR_String& matname,bool isDynamic,bool isActor); +static DT_ShapeHandle CreateShapeFromMesh(RAS_MeshObject* meshobj, bool polytope); + +void KX_ConvertSumoObject( KX_GameObject* gameobj, + RAS_MeshObject* meshobj, + KX_Scene* kxscene, + PHY_ShapeProps* kxshapeprops, + PHY_MaterialProps* kxmaterial, + struct KX_ObjectProperties* objprop) + + +{ + SM_ShapeProps* smprop = new SM_ShapeProps; + + smprop->m_ang_drag = kxshapeprops->m_ang_drag; + smprop->m_do_anisotropic = kxshapeprops->m_do_anisotropic; + smprop->m_do_fh = kxshapeprops->m_do_fh; + smprop->m_do_rot_fh = kxshapeprops->m_do_rot_fh ; + smprop->m_friction_scaling[0] = kxshapeprops->m_friction_scaling[0]; + smprop->m_friction_scaling[1] = kxshapeprops->m_friction_scaling[1]; + smprop->m_friction_scaling[2] = kxshapeprops->m_friction_scaling[2]; + smprop->m_inertia = MT_Vector3(1., 1., 1.) * kxshapeprops->m_inertia; + smprop->m_lin_drag = kxshapeprops->m_lin_drag; + smprop->m_mass = kxshapeprops->m_mass; + smprop->m_radius = objprop->m_radius; + + + SM_MaterialProps* smmaterial = new SM_MaterialProps; + + smmaterial->m_fh_damping = kxmaterial->m_fh_damping; + smmaterial->m_fh_distance = kxmaterial->m_fh_distance; + smmaterial->m_fh_normal = kxmaterial->m_fh_normal; + smmaterial->m_fh_spring = kxmaterial->m_fh_spring; + smmaterial->m_friction = kxmaterial->m_friction; + smmaterial->m_restitution = kxmaterial->m_restitution; + + SumoPhysicsEnvironment* sumoEnv = + (SumoPhysicsEnvironment*)kxscene->GetPhysicsEnvironment(); + + SM_Scene* sceneptr = sumoEnv->GetSumoScene(); + + SM_Object* sumoObj=NULL; + + if (objprop->m_dyna && objprop->m_isactor) + { + DT_ShapeHandle shape = NULL; + bool polytope = false; + switch (objprop->m_boundclass) + { + case KX_BOUNDBOX: + shape = DT_NewBox(objprop->m_boundobject.box.m_extends[0], + objprop->m_boundobject.box.m_extends[1], + objprop->m_boundobject.box.m_extends[2]); + smprop->m_inertia.scale(objprop->m_boundobject.box.m_extends[0]*objprop->m_boundobject.box.m_extends[0], + objprop->m_boundobject.box.m_extends[1]*objprop->m_boundobject.box.m_extends[1], + objprop->m_boundobject.box.m_extends[2]*objprop->m_boundobject.box.m_extends[2]); + smprop->m_inertia *= smprop->m_mass/MT_Vector3(objprop->m_boundobject.box.m_extends).length(); + break; + case KX_BOUNDCYLINDER: + shape = DT_NewCylinder(smprop->m_radius, objprop->m_boundobject.c.m_height); + smprop->m_inertia.scale(smprop->m_mass*smprop->m_radius*smprop->m_radius, + smprop->m_mass*smprop->m_radius*smprop->m_radius, + smprop->m_mass*objprop->m_boundobject.c.m_height*objprop->m_boundobject.c.m_height); + break; + case KX_BOUNDCONE: + shape = DT_NewCone(objprop->m_radius, objprop->m_boundobject.c.m_height); + smprop->m_inertia.scale(smprop->m_mass*smprop->m_radius*smprop->m_radius, + smprop->m_mass*smprop->m_radius*smprop->m_radius, + smprop->m_mass*objprop->m_boundobject.c.m_height*objprop->m_boundobject.c.m_height); + break; + /* Dynamic mesh objects. WARNING! slow. */ + case KX_BOUNDPOLYTOPE: + polytope = true; + // fall through + case KX_BOUNDMESH: + if (meshobj && meshobj->NumPolygons() > 0) + { + if ((shape = CreateShapeFromMesh(meshobj, polytope))) + { + // TODO: calculate proper inertia + smprop->m_inertia *= smprop->m_mass*smprop->m_radius*smprop->m_radius; + break; + } + } + /* If CreateShapeFromMesh fails, fall through and use sphere */ + default: + case KX_BOUNDSPHERE: + shape = DT_NewSphere(objprop->m_radius); + smprop->m_inertia *= smprop->m_mass*smprop->m_radius*smprop->m_radius; + break; + + } + + sumoObj = new SM_Object(shape, !objprop->m_ghost?smmaterial:NULL,smprop,NULL); + + sumoObj->setRigidBody(objprop->m_angular_rigidbody?true:false); + + BL_RegisterSumoObject(gameobj,sceneptr,sumoObj,"",true, true); + + } + else { + // non physics object + if (meshobj) + { + int numpolys = meshobj->NumPolygons(); + { + + DT_ShapeHandle complexshape=0; + bool polytope = false; + + switch (objprop->m_boundclass) + { + case KX_BOUNDBOX: + complexshape = DT_NewBox(objprop->m_boundobject.box.m_extends[0], objprop->m_boundobject.box.m_extends[1], objprop->m_boundobject.box.m_extends[2]); + break; + case KX_BOUNDSPHERE: + complexshape = DT_NewSphere(objprop->m_boundobject.c.m_radius); + break; + case KX_BOUNDCYLINDER: + complexshape = DT_NewCylinder(objprop->m_boundobject.c.m_radius, objprop->m_boundobject.c.m_height); + break; + case KX_BOUNDCONE: + complexshape = DT_NewCone(objprop->m_boundobject.c.m_radius, objprop->m_boundobject.c.m_height); + break; + case KX_BOUNDPOLYTOPE: + polytope = true; + // fall through + default: + case KX_BOUNDMESH: + if (numpolys>0) + { + complexshape = CreateShapeFromMesh(meshobj, polytope); + //std::cout << "Convert Physics Mesh: " << meshobj->GetName() << std::endl; +/* if (!complexshape) + { + // Something has to be done here - if the object has no polygons, it will not be able to have + // sensors attached to it. + DT_Vector3 pt = {0., 0., 0.}; + complexshape = DT_NewSphere(1.0); + objprop->m_ghost = evilObject = true; + } */ + } + break; + } + + if (complexshape) + { + SM_Object *dynamicParent = NULL; + + if (objprop->m_dynamic_parent) + { + // problem is how to find the dynamic parent + // in the scenegraph + KX_SumoPhysicsController* sumoctrl = + (KX_SumoPhysicsController*) + objprop->m_dynamic_parent->GetPhysicsController(); + + if (sumoctrl) + { + dynamicParent = sumoctrl->GetSumoObject(); + } + + MT_assert(dynamicParent); + } + + + sumoObj = new SM_Object(complexshape,!objprop->m_ghost?smmaterial:NULL,NULL, dynamicParent); + const STR_String& matname=meshobj->GetMaterialName(0); + + + BL_RegisterSumoObject(gameobj,sceneptr, + sumoObj, + matname, + objprop->m_dyna, + objprop->m_isactor); + } + } + } + } + + // physics object get updated here ! + + + // lazy evaluation because we might not support scaling !gameobj->UpdateTransform(); + + if (objprop->m_in_active_layer && sumoObj) + { + sceneptr->add(*sumoObj); + } + +} + + + +static void BL_RegisterSumoObject( + KX_GameObject* gameobj, + class SM_Scene* sumoScene, + class SM_Object* sumoObj, + const STR_String& matname, + bool isDynamic, + bool isActor) +{ + PHY_IMotionState* motionstate = new KX_MotionState(gameobj->GetSGNode()); + + // need easy access, not via 'node' etc. + KX_SumoPhysicsController* physicscontroller = new KX_SumoPhysicsController(sumoScene,sumoObj,motionstate,isDynamic); + gameobj->SetPhysicsController(physicscontroller,isDynamic); + + + if (!gameobj->getClientInfo()) + std::cout << "BL_RegisterSumoObject: WARNING: Object " << gameobj->GetName() << " has no client info" << std::endl; + physicscontroller->setNewClientInfo(gameobj->getClientInfo()); + + + gameobj->GetSGNode()->AddSGController(physicscontroller); + + gameobj->getClientInfo()->m_type = (isActor ? KX_ClientObjectInfo::ACTOR : KX_ClientObjectInfo::STATIC); + + // store materialname in auxinfo, needed for touchsensors + gameobj->getClientInfo()->m_auxilary_info = (matname.Length() ? (void*)(matname.ReadPtr()+2) : NULL); + + physicscontroller->SetObject(gameobj->GetSGNode()); +} + +static DT_ShapeHandle InstancePhysicsComplex(RAS_MeshObject* meshobj, RAS_DisplayArray *darray, RAS_IPolyMaterial *mat) +{ + // instance a mesh from a single vertex array & material + const RAS_TexVert *vertex_array = &darray->m_vertex[0]; + DT_VertexBaseHandle vertex_base = DT_NewVertexBase(vertex_array[0].getXYZ(), sizeof(RAS_TexVert)); + + DT_ShapeHandle shape = DT_NewComplexShape(vertex_base); + + std::vector<DT_Index> indices; + for (int p = 0; p < meshobj->NumPolygons(); p++) + { + RAS_Polygon* poly = meshobj->GetPolygon(p); + + // only add polygons that have the collisionflag set + if (poly->IsCollider()) + { + DT_Begin(); + DT_VertexIndex(poly->GetVertexOffset(0)); + DT_VertexIndex(poly->GetVertexOffset(1)); + DT_VertexIndex(poly->GetVertexOffset(2)); + DT_End(); + + // tesselate + if (poly->VertexCount() == 4) + { + DT_Begin(); + DT_VertexIndex(poly->GetVertexOffset(0)); + DT_VertexIndex(poly->GetVertexOffset(2)); + DT_VertexIndex(poly->GetVertexOffset(3)); + DT_End(); + } + } + } + + //DT_VertexIndices(indices.size(), &indices[0]); + DT_EndComplexShape(); + + map_gamemesh_to_instance.insert(GEN_HashedPtr(meshobj), new KX_PhysicsInstance(vertex_base, darray, mat)); + return shape; +} + +static DT_ShapeHandle InstancePhysicsPolytope(RAS_MeshObject* meshobj, RAS_DisplayArray *darray, RAS_IPolyMaterial *mat) +{ + // instance a mesh from a single vertex array & material + const RAS_TexVert *vertex_array = &darray->m_vertex[0]; + DT_VertexBaseHandle vertex_base = DT_NewVertexBase(vertex_array[0].getXYZ(), sizeof(RAS_TexVert)); + + std::vector<DT_Index> indices; + for (int p = 0; p < meshobj->NumPolygons(); p++) + { + RAS_Polygon* poly = meshobj->GetPolygon(p); + + // only add polygons that have the collisionflag set + if (poly->IsCollider()) + { + indices.push_back(poly->GetVertexOffset(0)); + indices.push_back(poly->GetVertexOffset(1)); + indices.push_back(poly->GetVertexOffset(2)); + + if (poly->VertexCount() == 4) + indices.push_back(poly->GetVertexOffset(3)); + } + } + + DT_ShapeHandle shape = DT_NewPolytope(vertex_base); + DT_VertexIndices(indices.size(), &indices[0]); + DT_EndPolytope(); + + map_gamemesh_to_instance.insert(GEN_HashedPtr(meshobj), new KX_PhysicsInstance(vertex_base, darray, mat)); + return shape; +} + +// This will have to be a method in a class somewhere... +// Update SOLID with a changed physics mesh. +// not used... yet. +bool KX_ReInstanceShapeFromMesh(RAS_MeshObject* meshobj) +{ + KX_PhysicsInstance *instance = *map_gamemesh_to_instance[GEN_HashedPtr(meshobj)]; + if (instance) + { + const RAS_TexVert *vertex_array = &instance->m_darray->m_vertex[0]; + DT_ChangeVertexBase(instance->m_vertexbase, vertex_array[0].getXYZ()); + return true; + } + return false; +} + +static DT_ShapeHandle CreateShapeFromMesh(RAS_MeshObject* meshobj, bool polytope) +{ + + DT_ShapeHandle *shapeptr = map_gamemesh_to_sumoshape[GEN_HashedPtr(meshobj)]; + // Mesh has already been converted: reuse + if (shapeptr) + { + return *shapeptr; + } + + // Mesh has no polygons! + int numpolys = meshobj->NumPolygons(); + if (!numpolys) + { + return NULL; + } + + // Count the number of collision polygons and check they all come from the same + // vertex array + int numvalidpolys = 0; + RAS_DisplayArray *darray = NULL; + RAS_IPolyMaterial *poly_material = NULL; + bool reinstance = true; + + for (int p=0; p<numpolys; p++) + { + RAS_Polygon* poly = meshobj->GetPolygon(p); + + // only add polygons that have the collisionflag set + if (poly->IsCollider()) + { + // check polygon is from the same vertex array + if (poly->GetDisplayArray() != darray) + { + if (darray == NULL) + darray = poly->GetDisplayArray(); + else + { + reinstance = false; + darray = NULL; + } + } + + // check poly is from the same material + if (poly->GetMaterial()->GetPolyMaterial() != poly_material) + { + if (poly_material) + { + reinstance = false; + poly_material = NULL; + } + else + poly_material = poly->GetMaterial()->GetPolyMaterial(); + } + + // count the number of collision polys + numvalidpolys++; + + // We have one collision poly, and we can't reinstance, so we + // might as well break here. + if (!reinstance) + break; + } + } + + // No collision polygons + if (numvalidpolys < 1) + return NULL; + + DT_ShapeHandle shape; + if (reinstance) + { + if (polytope) + shape = InstancePhysicsPolytope(meshobj, darray, poly_material); + else + shape = InstancePhysicsComplex(meshobj, darray, poly_material); + } + else + { + if (polytope) + { + std::cout << "CreateShapeFromMesh: " << meshobj->GetName() << " is not suitable for polytope." << std::endl; + if (!poly_material) + std::cout << " Check mesh materials." << std::endl; + if (darray == NULL) + std::cout << " Check number of vertices." << std::endl; + } + + shape = DT_NewComplexShape(NULL); + + numvalidpolys = 0; + + for (int p2=0; p2<numpolys; p2++) + { + RAS_Polygon* poly = meshobj->GetPolygon(p2); + + // only add polygons that have the collisionflag set + if (poly->IsCollider()) + { /* We have to tesselate here because SOLID can only raycast triangles */ + DT_Begin(); + /* V1, V2, V3 */ + DT_Vertex(poly->GetVertex(2)->getXYZ()); + DT_Vertex(poly->GetVertex(1)->getXYZ()); + DT_Vertex(poly->GetVertex(0)->getXYZ()); + + numvalidpolys++; + DT_End(); + + if (poly->VertexCount() == 4) + { + DT_Begin(); + /* V1, V3, V4 */ + DT_Vertex(poly->GetVertex(3)->getXYZ()); + DT_Vertex(poly->GetVertex(2)->getXYZ()); + DT_Vertex(poly->GetVertex(0)->getXYZ()); + + numvalidpolys++; + DT_End(); + } + + } + } + + DT_EndComplexShape(); + } + + if (numvalidpolys > 0) + { + map_gamemesh_to_sumoshape.insert(GEN_HashedPtr(meshobj),shape); + return shape; + } + + delete shape; + return NULL; +} + +void KX_ClearSumoSharedShapes() +{ + int numshapes = map_gamemesh_to_sumoshape.size(); + int i; + for (i=0;i<numshapes ;i++) + { + DT_ShapeHandle shape = *map_gamemesh_to_sumoshape.at(i); + DT_DeleteShape(shape); + } + + map_gamemesh_to_sumoshape.clear(); + + for (i=0; i < map_gamemesh_to_instance.size(); i++) + delete *map_gamemesh_to_instance.at(i); + + map_gamemesh_to_instance.clear(); +} + + + + + +#endif //USE_SUMO_SOLID + + +#ifdef USE_ODE + +void KX_ConvertODEEngineObject(KX_GameObject* gameobj, + RAS_MeshObject* meshobj, + KX_Scene* kxscene, + struct PHY_ShapeProps* shapeprops, + struct PHY_MaterialProps* smmaterial, + struct KX_ObjectProperties* objprop) +{ + + // not yet, future extension :) + bool dyna=objprop->m_dyna; + bool fullRigidBody= ( objprop->m_dyna && objprop->m_angular_rigidbody) != 0; + bool phantom = objprop->m_ghost; + class PHY_IMotionState* motionstate = new KX_MotionState(gameobj->GetSGNode()); + + class ODEPhysicsEnvironment* odeEnv = + (ODEPhysicsEnvironment*)kxscene->GetPhysicsEnvironment(); + + dxSpace* space = odeEnv->GetOdeSpace(); + dxWorld* world = odeEnv->GetOdeWorld(); + + bool isSphere = false; + + switch (objprop->m_boundclass) + { + case KX_BOUNDBOX: + { + + KX_OdePhysicsController* physicscontroller = + new KX_OdePhysicsController( + dyna, + fullRigidBody, + phantom, + motionstate, + space, + world, + shapeprops->m_mass, + smmaterial->m_friction, + smmaterial->m_restitution, + isSphere, + objprop->m_boundobject.box.m_center, + objprop->m_boundobject.box.m_extends, + objprop->m_boundobject.c.m_radius + ); + + gameobj->SetPhysicsController(physicscontroller); + physicscontroller->setNewClientInfo(gameobj->getClientInfo()); + gameobj->GetSGNode()->AddSGController(physicscontroller); + + bool isActor = objprop->m_isactor; + STR_String materialname; + if (meshobj) + materialname = meshobj->GetMaterialName(0); + + const char* matname = materialname.ReadPtr(); + + + physicscontroller->SetObject(gameobj->GetSGNode()); + + break; + } + default: + { + } + }; + +} + + +#endif // USE_ODE + + #ifdef USE_BULLET #include "CcdPhysicsEnvironment.h" diff --git a/source/gameengine/Ketsji/KX_GameActuator.cpp b/source/gameengine/Ketsji/KX_GameActuator.cpp index 560c7fa4bb4..28bf12f5e87 100644 --- a/source/gameengine/Ketsji/KX_GameActuator.cpp +++ b/source/gameengine/Ketsji/KX_GameActuator.cpp @@ -49,8 +49,9 @@ KX_GameActuator::KX_GameActuator(SCA_IObject *gameobj, const STR_String& filename, const STR_String& loadinganimationname, KX_Scene* scene, - KX_KetsjiEngine* ketsjiengine) - : SCA_IActuator(gameobj) + KX_KetsjiEngine* ketsjiengine, + PyTypeObject* T) + : SCA_IActuator(gameobj, T) { m_mode = mode; m_filename = filename; @@ -223,17 +224,26 @@ PyTypeObject KX_GameActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + + +PyParentObject KX_GameActuator::Parents[] = +{ + &KX_GameActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; + + PyMethodDef KX_GameActuator::Methods[] = { // Deprecated -----> @@ -249,6 +259,21 @@ PyAttributeDef KX_GameActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_GameActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_GameActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_GameActuator::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_IActuator); +} + + // Deprecated -----> /* getFile */ const char KX_GameActuator::GetFile_doc[] = @@ -257,7 +282,7 @@ const char KX_GameActuator::GetFile_doc[] = PyObject* KX_GameActuator::PyGetFile(PyObject* args, PyObject* kwds) { ShowDeprecationWarning("getFile()", "the fileName property"); - return PyUnicode_FromString(m_filename); + return PyString_FromString(m_filename); } /* setFile */ diff --git a/source/gameengine/Ketsji/KX_GameActuator.h b/source/gameengine/Ketsji/KX_GameActuator.h index cabbf827b40..b2b1d6ec2b9 100644 --- a/source/gameengine/Ketsji/KX_GameActuator.h +++ b/source/gameengine/Ketsji/KX_GameActuator.h @@ -65,7 +65,8 @@ protected: const STR_String& filename, const STR_String& loadinganimationname, KX_Scene* scene, - KX_KetsjiEngine* ketsjiEngine); + KX_KetsjiEngine* ketsjiEngine, + PyTypeObject* T=&Type); virtual ~KX_GameActuator(); virtual CValue* GetReplica(); @@ -76,6 +77,10 @@ protected: /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + // Deprecated functions -----> KX_PYMETHOD_DOC(KX_GameActuator,GetFile); KX_PYMETHOD_DOC(KX_GameActuator,SetFile); diff --git a/source/gameengine/Ketsji/KX_GameObject.cpp b/source/gameengine/Ketsji/KX_GameObject.cpp index bf80eec36d9..b266095c715 100644 --- a/source/gameengine/Ketsji/KX_GameObject.cpp +++ b/source/gameengine/Ketsji/KX_GameObject.cpp @@ -86,8 +86,10 @@ static MT_Matrix3x3 dummy_orientation = MT_Matrix3x3( 1.0, 0.0, 0.0, KX_GameObject::KX_GameObject( void* sgReplicationInfo, - SG_Callbacks callbacks) - : SCA_IObject(), + SG_Callbacks callbacks, + PyTypeObject* T +) : + SCA_IObject(T), m_bDyna(false), m_layer(0), m_pBlenderObject(NULL), @@ -981,17 +983,7 @@ void KX_GameObject::NodeSetLocalOrientation(const MT_Matrix3x3& rot) GetSGNode()->SetLocalOrientation(rot); } -void KX_GameObject::NodeSetGlobalOrientation(const MT_Matrix3x3& rot) -{ - // check on valid node in case a python controller holds a reference to a deleted object - if (!GetSGNode()) - return; - if (GetSGNode()->GetSGParent()) - GetSGNode()->SetLocalOrientation(GetSGNode()->GetSGParent()->GetWorldOrientation().inverse()*rot); - else - GetSGNode()->SetLocalOrientation(rot); -} void KX_GameObject::NodeSetLocalScale(const MT_Vector3& scale) { @@ -1070,13 +1062,7 @@ const MT_Matrix3x3& KX_GameObject::NodeGetWorldOrientation() const return GetSGNode()->GetWorldOrientation(); } -const MT_Matrix3x3& KX_GameObject::NodeGetLocalOrientation() const -{ - // check on valid node in case a python controller holds a reference to a deleted object - if (!GetSGNode()) - return dummy_orientation; - return GetSGNode()->GetLocalOrientation(); -} + const MT_Vector3& KX_GameObject::NodeGetWorldScaling() const { @@ -1087,14 +1073,7 @@ const MT_Vector3& KX_GameObject::NodeGetWorldScaling() const return GetSGNode()->GetWorldScaling(); } -const MT_Vector3& KX_GameObject::NodeGetLocalScaling() const -{ - // check on valid node in case a python controller holds a reference to a deleted object - if (!GetSGNode()) - return dummy_scaling; - return GetSGNode()->GetLocalScale(); -} const MT_Point3& KX_GameObject::NodeGetWorldPosition() const { @@ -1105,16 +1084,6 @@ const MT_Point3& KX_GameObject::NodeGetWorldPosition() const return dummy_point; } -const MT_Point3& KX_GameObject::NodeGetLocalPosition() const -{ - // check on valid node in case a python controller holds a reference to a deleted object - if (GetSGNode()) - return GetSGNode()->GetLocalPosition(); - else - return dummy_point; -} - - /* Suspend/ resume: for the dynamic behaviour, there is a simple * method. For the residual motion, there is not. I wonder what the * correct solution is for Sumo. Remove from the motion-update tree? @@ -1182,181 +1151,6 @@ CListValue* KX_GameObject::GetChildrenRecursive() return list; } -#ifdef USE_MATHUTILS - -/* These require an SGNode */ -#define MATHUTILS_VEC_CB_POS_LOCAL 1 -#define MATHUTILS_VEC_CB_POS_GLOBAL 2 -#define MATHUTILS_VEC_CB_SCALE_LOCAL 3 -#define MATHUTILS_VEC_CB_SCALE_GLOBAL 4 -#define MATHUTILS_VEC_CB_INERTIA_LOCAL 5 - -static int mathutils_kxgameob_vector_cb_index= -1; /* index for our callbacks */ - -static int mathutils_kxgameob_generic_check(PyObject *self_v) -{ - KX_GameObject* self= static_cast<KX_GameObject*>BGE_PROXY_REF(self_v); - if(self==NULL) - return 0; - - return 1; -} - -static int mathutils_kxgameob_vector_get(PyObject *self_v, int subtype, float *vec_from) -{ - KX_GameObject* self= static_cast<KX_GameObject*>BGE_PROXY_REF(self_v); - if(self==NULL) - return 0; - - switch(subtype) { - case MATHUTILS_VEC_CB_POS_LOCAL: - self->NodeGetLocalPosition().getValue(vec_from); - break; - case MATHUTILS_VEC_CB_POS_GLOBAL: - self->NodeGetWorldPosition().getValue(vec_from); - break; - case MATHUTILS_VEC_CB_SCALE_LOCAL: - self->NodeGetLocalScaling().getValue(vec_from); - break; - case MATHUTILS_VEC_CB_SCALE_GLOBAL: - self->NodeGetWorldScaling().getValue(vec_from); - break; - case MATHUTILS_VEC_CB_INERTIA_LOCAL: - if(!self->GetPhysicsController()) return 0; - self->GetPhysicsController()->GetLocalInertia().getValue(vec_from); - break; - } - - return 1; -} - -static int mathutils_kxgameob_vector_set(PyObject *self_v, int subtype, float *vec_to) -{ - KX_GameObject* self= static_cast<KX_GameObject*>BGE_PROXY_REF(self_v); - if(self==NULL) - return 0; - - switch(subtype) { - case MATHUTILS_VEC_CB_POS_LOCAL: - self->NodeSetLocalPosition(MT_Point3(vec_to)); - self->NodeUpdateGS(0.f); - break; - case MATHUTILS_VEC_CB_POS_GLOBAL: - self->NodeSetWorldPosition(MT_Point3(vec_to)); - self->NodeUpdateGS(0.f); - break; - case MATHUTILS_VEC_CB_SCALE_LOCAL: - self->NodeSetLocalScale(MT_Point3(vec_to)); - self->NodeUpdateGS(0.f); - break; - case MATHUTILS_VEC_CB_SCALE_GLOBAL: - break; - case MATHUTILS_VEC_CB_INERTIA_LOCAL: - /* read only */ - break; - } - - return 1; -} - -static int mathutils_kxgameob_vector_get_index(PyObject *self_v, int subtype, float *vec_from, int index) -{ - float f[4]; - /* lazy, avoid repeteing the case statement */ - if(!mathutils_kxgameob_vector_get(self_v, subtype, f)) - return 0; - - vec_from[index]= f[index]; - return 1; -} - -static int mathutils_kxgameob_vector_set_index(PyObject *self_v, int subtype, float *vec_to, int index) -{ - float f= vec_to[index]; - - /* lazy, avoid repeteing the case statement */ - if(!mathutils_kxgameob_vector_get(self_v, subtype, vec_to)) - return 0; - - vec_to[index]= f; - mathutils_kxgameob_vector_set(self_v, subtype, vec_to); - - return 1; -} - -Mathutils_Callback mathutils_kxgameob_vector_cb = { - mathutils_kxgameob_generic_check, - mathutils_kxgameob_vector_get, - mathutils_kxgameob_vector_set, - mathutils_kxgameob_vector_get_index, - mathutils_kxgameob_vector_set_index -}; - -/* Matrix */ -#define MATHUTILS_MAT_CB_ORI_LOCAL 1 -#define MATHUTILS_MAT_CB_ORI_GLOBAL 2 - -static int mathutils_kxgameob_matrix_cb_index= -1; /* index for our callbacks */ - -static int mathutils_kxgameob_matrix_get(PyObject *self_v, int subtype, float *mat_from) -{ - KX_GameObject* self= static_cast<KX_GameObject*>BGE_PROXY_REF(self_v); - if(self==NULL) - return 0; - - switch(subtype) { - case MATHUTILS_MAT_CB_ORI_LOCAL: - self->NodeGetLocalOrientation().getValue3x3(mat_from); - break; - case MATHUTILS_MAT_CB_ORI_GLOBAL: - self->NodeGetWorldOrientation().getValue3x3(mat_from); - break; - } - - return 1; -} - - -static int mathutils_kxgameob_matrix_set(PyObject *self_v, int subtype, float *mat_to) -{ - KX_GameObject* self= static_cast<KX_GameObject*>BGE_PROXY_REF(self_v); - if(self==NULL) - return 0; - - MT_Matrix3x3 mat3x3; - switch(subtype) { - case MATHUTILS_MAT_CB_ORI_LOCAL: - mat3x3.setValue3x3(mat_to); - self->NodeSetLocalOrientation(mat3x3); - self->NodeUpdateGS(0.f); - break; - case MATHUTILS_MAT_CB_ORI_GLOBAL: - mat3x3.setValue3x3(mat_to); - self->NodeSetLocalOrientation(mat3x3); - self->NodeUpdateGS(0.f); - break; - } - - return 1; -} - -Mathutils_Callback mathutils_kxgameob_matrix_cb = { - mathutils_kxgameob_generic_check, - mathutils_kxgameob_matrix_get, - mathutils_kxgameob_matrix_set, - NULL, - NULL -}; - - -void KX_GameObject_Mathutils_Callback_Init(void) -{ - // register mathutils callbacks, ok to run more then once. - mathutils_kxgameob_vector_cb_index= Mathutils_RegisterCallback(&mathutils_kxgameob_vector_cb); - mathutils_kxgameob_matrix_cb_index= Mathutils_RegisterCallback(&mathutils_kxgameob_matrix_cb); -} - -#endif // USE_MATHUTILS /* ------- python stuff ---------------------------------------------------*/ @@ -1496,7 +1290,7 @@ PyObject* KX_GameObject::PyGetPosition() static PyObject *Map_GetItem(PyObject *self_v, PyObject *item) { KX_GameObject* self= static_cast<KX_GameObject*>BGE_PROXY_REF(self_v); - const char *attr_str= _PyUnicode_AsString(item); + const char *attr_str= PyString_AsString(item); CValue* resultattr; PyObject* pyconvert; @@ -1530,7 +1324,7 @@ static PyObject *Map_GetItem(PyObject *self_v, PyObject *item) static int Map_SetItem(PyObject *self_v, PyObject *key, PyObject *val) { KX_GameObject* self= static_cast<KX_GameObject*>BGE_PROXY_REF(self_v); - const char *attr_str= _PyUnicode_AsString(key); + const char *attr_str= PyString_AsString(key); if(attr_str==NULL) PyErr_Clear(); @@ -1562,7 +1356,7 @@ static int Map_SetItem(PyObject *self_v, PyObject *key, PyObject *val) int set= 0; /* as CValue */ - if(attr_str && PyObject_TypeCheck(val, &PyObjectPlus::Type)==0) /* dont allow GameObjects for eg to be assigned to CValue props */ + if(attr_str && BGE_PROXY_CHECK_TYPE(val)==0) /* dont allow GameObjects for eg to be assigned to CValue props */ { CValue* vallie = self->ConvertPythonToValue(val, ""); /* error unused */ @@ -1624,7 +1418,7 @@ static int Seq_Contains(PyObject *self_v, PyObject *value) return -1; } - if(PyUnicode_Check(value) && self->GetProperty(_PyUnicode_AsString(value))) + if(PyString_Check(value) && self->GetProperty(PyString_AsString(value))) return 1; if (self->m_attr_dict && PyDict_GetItem(self->m_attr_dict, value)) @@ -1672,23 +1466,30 @@ PyTypeObject KX_GameObject::Type = { &Sequence, &Mapping, 0,0,0, - NULL, - NULL, + py_base_getattro, + py_base_setattro, 0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, + Py_TPFLAGS_DEFAULT, 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + + + + + +PyParentObject KX_GameObject::Parents[] = { + &KX_GameObject::Type, &SCA_IObject::Type, - 0,0,0,0,0,0, - py_base_new + &CValue::Type, + NULL }; PyObject* KX_GameObject::pyattr_get_name(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_GameObject* self= static_cast<KX_GameObject*>(self_v); - return PyUnicode_FromString(self->GetName().ReadPtr()); + return PyString_FromString(self->GetName().ReadPtr()); } PyObject* KX_GameObject::pyattr_get_parent(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) @@ -1795,11 +1596,7 @@ int KX_GameObject::pyattr_set_visible(void *self_v, const KX_PYATTRIBUTE_DEF *at PyObject* KX_GameObject::pyattr_get_worldPosition(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_GameObject* self= static_cast<KX_GameObject*>(self_v); -#ifdef USE_MATHUTILS - return newVectorObject_cb((PyObject *)self_v, 3, mathutils_kxgameob_vector_cb_index, MATHUTILS_VEC_CB_POS_GLOBAL); -#else return PyObjectFrom(self->NodeGetWorldPosition()); -#endif } int KX_GameObject::pyattr_set_worldPosition(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) @@ -1817,11 +1614,10 @@ int KX_GameObject::pyattr_set_worldPosition(void *self_v, const KX_PYATTRIBUTE_D PyObject* KX_GameObject::pyattr_get_localPosition(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_GameObject* self= static_cast<KX_GameObject*>(self_v); -#ifdef USE_MATHUTILS - return newVectorObject_cb((PyObject *)self_v, 3, mathutils_kxgameob_vector_cb_index, MATHUTILS_VEC_CB_POS_LOCAL); -#else - return PyObjectFrom(self->NodeGetLocalPosition()); -#endif + if (self->GetSGNode()) + return PyObjectFrom(self->GetSGNode()->GetLocalPosition()); + else + return PyObjectFrom(dummy_point); } int KX_GameObject::pyattr_set_localPosition(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) @@ -1839,23 +1635,17 @@ int KX_GameObject::pyattr_set_localPosition(void *self_v, const KX_PYATTRIBUTE_D PyObject* KX_GameObject::pyattr_get_localInertia(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_GameObject* self= static_cast<KX_GameObject*>(self_v); -#ifdef USE_MATHUTILS - return newVectorObject_cb((PyObject *)self_v, 3, mathutils_kxgameob_vector_cb_index, MATHUTILS_VEC_CB_INERTIA_LOCAL); -#else if (self->GetPhysicsController()) + { return PyObjectFrom(self->GetPhysicsController()->GetLocalInertia()); + } return Py_BuildValue("fff", 0.0f, 0.0f, 0.0f); -#endif } PyObject* KX_GameObject::pyattr_get_worldOrientation(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { -#ifdef USE_MATHUTILS - return newMatrixObject_cb((PyObject *)self_v, 3, 3, mathutils_kxgameob_matrix_cb_index, MATHUTILS_MAT_CB_ORI_GLOBAL); -#else KX_GameObject* self= static_cast<KX_GameObject*>(self_v); return PyObjectFrom(self->NodeGetWorldOrientation()); -#endif } int KX_GameObject::pyattr_set_worldOrientation(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) @@ -1867,7 +1657,12 @@ int KX_GameObject::pyattr_set_worldOrientation(void *self_v, const KX_PYATTRIBUT if (!PyOrientationTo(value, rot, "gameOb.worldOrientation = sequence: KX_GameObject, ")) return PY_SET_ATTR_FAIL; - self->NodeSetGlobalOrientation(rot); + if (self->GetSGNode() && self->GetSGNode()->GetSGParent()) { + self->NodeSetLocalOrientation(self->GetSGNode()->GetSGParent()->GetWorldOrientation().inverse()*rot); + } + else { + self->NodeSetLocalOrientation(rot); + } self->NodeUpdateGS(0.f); return PY_SET_ATTR_SUCCESS; @@ -1875,12 +1670,11 @@ int KX_GameObject::pyattr_set_worldOrientation(void *self_v, const KX_PYATTRIBUT PyObject* KX_GameObject::pyattr_get_localOrientation(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { -#ifdef USE_MATHUTILS - return newMatrixObject_cb((PyObject *)self_v, 3, 3, mathutils_kxgameob_matrix_cb_index, MATHUTILS_MAT_CB_ORI_LOCAL); -#else KX_GameObject* self= static_cast<KX_GameObject*>(self_v); - return PyObjectFrom(self->NodeGetLocalOrientation()); -#endif + if (self->GetSGNode()) + return PyObjectFrom(self->GetSGNode()->GetLocalOrientation()); + else + return PyObjectFrom(dummy_orientation); } int KX_GameObject::pyattr_set_localOrientation(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) @@ -1900,21 +1694,16 @@ int KX_GameObject::pyattr_set_localOrientation(void *self_v, const KX_PYATTRIBUT PyObject* KX_GameObject::pyattr_get_worldScaling(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_GameObject* self= static_cast<KX_GameObject*>(self_v); -#ifdef USE_MATHUTILS - return newVectorObject_cb((PyObject *)self_v, 3, mathutils_kxgameob_vector_cb_index, MATHUTILS_VEC_CB_SCALE_GLOBAL); -#else return PyObjectFrom(self->NodeGetWorldScaling()); -#endif } PyObject* KX_GameObject::pyattr_get_localScaling(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_GameObject* self= static_cast<KX_GameObject*>(self_v); -#ifdef USE_MATHUTILS - return newVectorObject_cb((PyObject *)self_v, 3, mathutils_kxgameob_vector_cb_index, MATHUTILS_VEC_CB_SCALE_LOCAL); -#else - return PyObjectFrom(self->NodeGetLocalScaling()); -#endif + if (self->GetSGNode()) + return PyObjectFrom(self->GetSGNode()->GetLocalScale()); + else + return PyObjectFrom(dummy_scaling); } int KX_GameObject::pyattr_set_localScaling(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) @@ -1961,13 +1750,13 @@ PyObject* KX_GameObject::pyattr_get_state(void *self_v, const KX_PYATTRIBUTE_DEF KX_GameObject* self= static_cast<KX_GameObject*>(self_v); int state = 0; state |= self->GetState(); - return PyLong_FromSsize_t(state); + return PyInt_FromLong(state); } int KX_GameObject::pyattr_set_state(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) { KX_GameObject* self= static_cast<KX_GameObject*>(self_v); - int state_i = PyLong_AsSsize_t(value); + int state_i = PyInt_AsLong(value); unsigned int state = 0; if (state_i == -1 && PyErr_Occurred()) { @@ -2038,6 +1827,128 @@ PyObject* KX_GameObject::pyattr_get_attrDict(void *self_v, const KX_PYATTRIBUTE_ return self->m_attr_dict; } +/* We need these because the macros have a return in them */ +PyObject* KX_GameObject::py_getattro__internal(PyObject *attr) +{ + py_getattro_up(SCA_IObject); +} + +int KX_GameObject::py_setattro__internal(PyObject *attr, PyObject *value) // py_setattro method +{ + py_setattro_up(SCA_IObject); +} + + +PyObject* KX_GameObject::py_getattro(PyObject *attr) +{ + PyObject *object= py_getattro__internal(attr); + + if (object==NULL && m_attr_dict) + { + /* backup the exception incase the attr doesnt exist in the dict either */ + PyObject *err_type, *err_value, *err_tb; + PyErr_Fetch(&err_type, &err_value, &err_tb); + + object= PyDict_GetItem(m_attr_dict, attr); + if (object) { + Py_INCREF(object); + + PyErr_Clear(); + Py_XDECREF( err_type ); + Py_XDECREF( err_value ); + Py_XDECREF( err_tb ); + } + else { + PyErr_Restore(err_type, err_value, err_tb); /* use the error from the parent function */ + } + } + return object; +} + +PyObject* KX_GameObject::py_getattro_dict() { + //py_getattro_dict_up(SCA_IObject); + PyObject *dict= py_getattr_dict(SCA_IObject::py_getattro_dict(), Type.tp_dict); + if(dict==NULL) + return NULL; + + /* normally just return this but KX_GameObject has some more items */ + + + /* Not super fast getting as a list then making into dict keys but its only for dir() */ + PyObject *list= ConvertKeysToPython(); + if(list) + { + int i; + for(i=0; i<PyList_Size(list); i++) + PyDict_SetItem(dict, PyList_GET_ITEM(list, i), Py_None); + } + else + PyErr_Clear(); + + Py_DECREF(list); + + /* Add m_attr_dict if we have it */ + if(m_attr_dict) + PyDict_Update(dict, m_attr_dict); + + return dict; +} + +int KX_GameObject::py_setattro(PyObject *attr, PyObject *value) // py_setattro method +{ + int ret= py_setattro__internal(attr, value); + + if (ret==PY_SET_ATTR_SUCCESS) { + /* remove attribute in our own dict to avoid double ups */ + /* NOTE: Annoying that we also do this for setting builtin attributes like mass and visibility :/ */ + if (m_attr_dict) { + if (PyDict_DelItem(m_attr_dict, attr) != 0) + PyErr_Clear(); + } + } + + if (ret==PY_SET_ATTR_COERCE_FAIL) { + /* CValue attribute exists, remove CValue and add PyDict value */ + RemoveProperty(PyString_AsString(attr)); + ret= PY_SET_ATTR_MISSING; + } + + if (ret==PY_SET_ATTR_MISSING) { + /* Lazy initialization */ + if (m_attr_dict==NULL) + m_attr_dict = PyDict_New(); + + if (PyDict_SetItem(m_attr_dict, attr, value)==0) { + PyErr_Clear(); + ret= PY_SET_ATTR_SUCCESS; + } + else { + PyErr_Format(PyExc_AttributeError, "gameOb.myAttr = value: KX_GameObject, failed assigning value to internal dictionary"); + ret= PY_SET_ATTR_FAIL; + } + } + + return ret; +} + + +int KX_GameObject::py_delattro(PyObject *attr) +{ + ShowDeprecationWarning("del ob.attr", "del ob['attr'] for user defined properties"); + + char *attr_str= PyString_AsString(attr); + + if (RemoveProperty(attr_str)) // XXX - should call CValues instead but its only 2 lines here + return PY_SET_ATTR_SUCCESS; + + if (m_attr_dict && (PyDict_DelItem(m_attr_dict, attr) == 0)) + return PY_SET_ATTR_SUCCESS; + + PyErr_Format(PyExc_AttributeError, "del gameOb.myAttr: KX_GameObject, attribute \"%s\" dosnt exist", attr_str); + return PY_SET_ATTR_MISSING; +} + + PyObject* KX_GameObject::PyApplyForce(PyObject* args) { int local = 0; @@ -2181,7 +2092,7 @@ PyObject* KX_GameObject::PySetOcclusion(PyObject* args) PyObject* KX_GameObject::PyGetVisible() { ShowDeprecationWarning("getVisible()", "the visible property"); - return PyLong_FromSsize_t(m_bVisible); + return PyInt_FromLong(m_bVisible); } PyObject* KX_GameObject::PyGetState() @@ -2189,13 +2100,13 @@ PyObject* KX_GameObject::PyGetState() ShowDeprecationWarning("getState()", "the state property"); int state = 0; state |= GetState(); - return PyLong_FromSsize_t(state); + return PyInt_FromLong(state); } PyObject* KX_GameObject::PySetState(PyObject* value) { ShowDeprecationWarning("setState()", "the state property"); - int state_i = PyLong_AsSsize_t(value); + int state_i = PyInt_AsLong(value); unsigned int state = 0; if (state_i == -1 && PyErr_Occurred()) { @@ -2501,7 +2412,7 @@ PyObject* KX_GameObject::PyGetPhysicsId() { physid= (uint_ptr)ctrl->GetUserData(); } - return PyLong_FromSsize_t((long)physid); + return PyInt_FromLong((long)physid); } PyObject* KX_GameObject::PyGetPropertyNames() @@ -2877,8 +2788,8 @@ PyObject* KX_GameObject::Pyget(PyObject *args) return NULL; - if(PyUnicode_Check(key)) { - CValue *item = GetProperty(_PyUnicode_AsString(key)); + if(PyString_Check(key)) { + CValue *item = GetProperty(PyString_AsString(key)); if (item) { ret = item->ConvertValueToPython(); if(ret) @@ -2947,13 +2858,13 @@ bool ConvertPythonToGameObject(PyObject * value, KX_GameObject **object, bool py } } - if (PyUnicode_Check(value)) { - *object = (KX_GameObject*)SCA_ILogicBrick::m_sCurrentLogicManager->GetGameObjectByName(STR_String( _PyUnicode_AsString(value) )); + if (PyString_Check(value)) { + *object = (KX_GameObject*)SCA_ILogicBrick::m_sCurrentLogicManager->GetGameObjectByName(STR_String( PyString_AsString(value) )); if (*object) { return true; } else { - PyErr_Format(PyExc_ValueError, "%s, requested name \"%s\" did not match any KX_GameObject in this scene", error_prefix, _PyUnicode_AsString(value)); + PyErr_Format(PyExc_ValueError, "%s, requested name \"%s\" did not match any KX_GameObject in this scene", error_prefix, PyString_AsString(value)); return false; } } diff --git a/source/gameengine/Ketsji/KX_GameObject.h b/source/gameengine/Ketsji/KX_GameObject.h index 947cc9959ff..ff5c8a01e6e 100644 --- a/source/gameengine/Ketsji/KX_GameObject.h +++ b/source/gameengine/Ketsji/KX_GameObject.h @@ -63,10 +63,6 @@ struct Object; /* utility conversion function */ bool ConvertPythonToGameObject(PyObject * value, KX_GameObject **object, bool py_none_ok, const char *error_prefix); -#ifdef USE_MATHUTILS -void KX_GameObject_Mathutils_Callback_Init(void); -#endif - /** * KX_GameObject is the main class for dynamic objects. */ @@ -189,7 +185,8 @@ public: KX_GameObject( void* sgReplicationInfo, - SG_Callbacks callbacks + SG_Callbacks callbacks, + PyTypeObject* T=&Type ); virtual @@ -396,7 +393,6 @@ public: void NodeSetLocalPosition(const MT_Point3& trans ); void NodeSetLocalOrientation(const MT_Matrix3x3& rot ); - void NodeSetGlobalOrientation(const MT_Matrix3x3& rot ); void NodeSetLocalScale( const MT_Vector3& scale ); @@ -410,13 +406,21 @@ public: double time ); - const MT_Matrix3x3& NodeGetWorldOrientation( ) const; - const MT_Vector3& NodeGetWorldScaling( ) const; - const MT_Point3& NodeGetWorldPosition( ) const; + const + MT_Matrix3x3& + NodeGetWorldOrientation( + ) const; + + const + MT_Vector3& + NodeGetWorldScaling( + ) const; + + const + MT_Point3& + NodeGetWorldPosition( + ) const; - const MT_Matrix3x3& NodeGetLocalOrientation( ) const; - const MT_Vector3& NodeGetLocalScaling( ) const; - const MT_Point3& NodeGetLocalPosition( ) const; /** * @section scene graph node accessor functions. @@ -807,10 +811,22 @@ public: /** * @section Python interface functions. */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); // py_setattro method + virtual int py_delattro(PyObject *attr); virtual PyObject* py_repr(void) { - return PyUnicode_FromString(GetName().ReadPtr()); + return PyString_FromString(GetName().ReadPtr()); } + + + /* quite annoying that we need these but the bloody + * py_getattro_up and py_setattro_up macro's have a returns in them! */ + PyObject* py_getattro__internal(PyObject *attr); + int py_setattro__internal(PyObject *attr, PyObject *value); // py_setattro method + KX_PYMETHOD_NOARGS(KX_GameObject,GetPosition); KX_PYMETHOD_O(KX_GameObject,SetPosition); diff --git a/source/gameengine/Ketsji/KX_IpoActuator.cpp b/source/gameengine/Ketsji/KX_IpoActuator.cpp index 73a370a1681..3ec0598ac03 100644 --- a/source/gameengine/Ketsji/KX_IpoActuator.cpp +++ b/source/gameengine/Ketsji/KX_IpoActuator.cpp @@ -70,8 +70,9 @@ KX_IpoActuator::KX_IpoActuator(SCA_IObject* gameobj, int acttype, bool ipo_as_force, bool ipo_add, - bool ipo_local) - : SCA_IActuator(gameobj), + bool ipo_local, + PyTypeObject* T) + : SCA_IActuator(gameobj,T), m_bNegativeEvent(false), m_startframe (starttime), m_endframe(endtime), @@ -428,15 +429,19 @@ PyTypeObject KX_IpoActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_IpoActuator::Parents[] = { + &KX_IpoActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_IpoActuator::Methods[] = { @@ -472,6 +477,18 @@ PyAttributeDef KX_IpoActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_IpoActuator::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_IpoActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_IpoActuator::py_setattro(PyObject *attr, PyObject *value) // py_setattro method +{ + py_setattro_up(SCA_IActuator); +} /* set --------------------------------------------------------------------- */ const char KX_IpoActuator::Set_doc[] = @@ -672,7 +689,7 @@ const char KX_IpoActuator::GetType_doc[] = "\tReturns the operation mode of the actuator.\n"; PyObject* KX_IpoActuator::PyGetType() { ShowDeprecationWarning("getType()", "the mode property"); - return PyLong_FromSsize_t(m_type); + return PyInt_FromLong(m_type); } /* 10. setForceIpoActsLocal: */ diff --git a/source/gameengine/Ketsji/KX_IpoActuator.h b/source/gameengine/Ketsji/KX_IpoActuator.h index 01051ca82dc..9ea597def1e 100644 --- a/source/gameengine/Ketsji/KX_IpoActuator.h +++ b/source/gameengine/Ketsji/KX_IpoActuator.h @@ -121,7 +121,8 @@ public: int acttype, bool ipo_as_force, bool ipo_add, - bool ipo_local); + bool ipo_local, + PyTypeObject* T=&Type); virtual ~KX_IpoActuator() {}; virtual CValue* GetReplica() { @@ -137,6 +138,10 @@ public: /* --------------------------------------------------------------------- */ /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); //KX_PYMETHOD_DOC KX_PYMETHOD_DOC_VARARGS(KX_IpoActuator,Set); diff --git a/source/gameengine/Ketsji/KX_KetsjiEngine.cpp b/source/gameengine/Ketsji/KX_KetsjiEngine.cpp index cc0f50d9e7a..a43ea59220b 100644 --- a/source/gameengine/Ketsji/KX_KetsjiEngine.cpp +++ b/source/gameengine/Ketsji/KX_KetsjiEngine.cpp @@ -61,6 +61,10 @@ #include "KX_PyConstraintBinding.h" #include "PHY_IPhysicsEnvironment.h" +#ifdef USE_SUMO_SOLID +#include "SumoPhysicsEnvironment.h" +#endif + #include "SND_Scene.h" #include "SND_IAudioDevice.h" @@ -396,9 +400,9 @@ void KX_KetsjiEngine::StartEngine(bool clearIpo) World* world = m_scenes[0]->GetBlenderScene()->world; if (world) { - m_ticrate = world->ticrate ? world->ticrate : DEFAULT_LOGIC_TIC_RATE; - m_maxLogicFrame = world->maxlogicstep ? world->maxlogicstep : 5; - m_maxPhysicsFrame = world->maxphystep ? world->maxlogicstep : 5; + m_ticrate = world->ticrate; + m_maxLogicFrame = world->maxlogicstep; + m_maxPhysicsFrame = world->maxphystep; } else { diff --git a/source/gameengine/Ketsji/KX_Light.cpp b/source/gameengine/Ketsji/KX_Light.cpp index fb385f8a9a2..ae9e097a96e 100644 --- a/source/gameengine/Ketsji/KX_Light.cpp +++ b/source/gameengine/Ketsji/KX_Light.cpp @@ -51,9 +51,12 @@ KX_LightObject::KX_LightObject(void* sgReplicationInfo,SG_Callbacks callbacks, class RAS_IRenderTools* rendertools, const RAS_LightObject& lightobj, - bool glsl) - : KX_GameObject(sgReplicationInfo,callbacks), - m_rendertools(rendertools) + bool glsl, + PyTypeObject* T + ) + : + KX_GameObject(sgReplicationInfo,callbacks,T), + m_rendertools(rendertools) { m_lightobj = lightobj; m_lightobj.m_scene = sgReplicationInfo; @@ -268,6 +271,11 @@ void KX_LightObject::UnbindShadowBuffer(RAS_IRasterizer *ras) /* Python Integration Hooks */ /* ------------------------------------------------------------------------- */ +PyObject* KX_LightObject::py_getattro_dict() { + py_getattro_dict_up(KX_GameObject); +} + + PyTypeObject KX_LightObject::Type = { #if (PY_VERSION_HEX >= 0x02060000) PyVarObject_HEAD_INIT(NULL, 0) @@ -289,17 +297,20 @@ PyTypeObject KX_LightObject::Type = { &KX_GameObject::Sequence, &KX_GameObject::Mapping, 0,0,0, - NULL, - NULL, + py_base_getattro, + py_base_setattro, 0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, + Py_TPFLAGS_DEFAULT, 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &KX_GameObject::Type, - 0,0,0,0,0,0, - py_base_new + Methods +}; + +PyParentObject KX_LightObject::Parents[] = { + &KX_LightObject::Type, + &KX_GameObject::Type, + &SCA_IObject::Type, + &CValue::Type, + NULL }; PyMethodDef KX_LightObject::Methods[] = { @@ -351,11 +362,11 @@ PyObject* KX_LightObject::pyattr_get_typeconst(void *self_v, const KX_PYATTRIBUT const char* type = attrdef->m_name; if(strcmp(type, "SPOT")) { - retvalue = PyLong_FromSsize_t(RAS_LightObject::LIGHT_SPOT); + retvalue = PyInt_FromLong(RAS_LightObject::LIGHT_SPOT); } else if (strcmp(type, "SUN")) { - retvalue = PyLong_FromSsize_t(RAS_LightObject::LIGHT_SUN); + retvalue = PyInt_FromLong(RAS_LightObject::LIGHT_SUN); } else if (strcmp(type, "NORMAL")) { - retvalue = PyLong_FromSsize_t(RAS_LightObject::LIGHT_NORMAL); + retvalue = PyInt_FromLong(RAS_LightObject::LIGHT_NORMAL); } return retvalue; @@ -364,13 +375,13 @@ PyObject* KX_LightObject::pyattr_get_typeconst(void *self_v, const KX_PYATTRIBUT PyObject* KX_LightObject::pyattr_get_type(void* self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_LightObject* self = static_cast<KX_LightObject*>(self_v); - return PyLong_FromSsize_t(self->m_lightobj.m_type); + return PyInt_FromLong(self->m_lightobj.m_type); } int KX_LightObject::pyattr_set_type(void* self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject* value) { KX_LightObject* self = static_cast<KX_LightObject*>(self_v); - int val = PyLong_AsSsize_t(value); + int val = PyInt_AsLong(value); if((val==-1 && PyErr_Occurred()) || val<0 || val>2) { PyErr_SetString(PyExc_ValueError, "light.type= val: KX_LightObject, expected an int between 0 and 2"); return PY_SET_ATTR_FAIL; @@ -390,3 +401,14 @@ int KX_LightObject::pyattr_set_type(void* self_v, const KX_PYATTRIBUTE_DEF *attr return PY_SET_ATTR_SUCCESS; } + + +PyObject* KX_LightObject::py_getattro(PyObject *attr) +{ + py_getattro_up(KX_GameObject); +} + +int KX_LightObject::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(KX_GameObject); +} diff --git a/source/gameengine/Ketsji/KX_Light.h b/source/gameengine/Ketsji/KX_Light.h index 0b7ccbe81ab..358c705080a 100644 --- a/source/gameengine/Ketsji/KX_Light.h +++ b/source/gameengine/Ketsji/KX_Light.h @@ -49,7 +49,7 @@ protected: Scene* m_blenderscene; public: - KX_LightObject(void* sgReplicationInfo,SG_Callbacks callbacks,class RAS_IRenderTools* rendertools,const struct RAS_LightObject& lightobj, bool glsl); + KX_LightObject(void* sgReplicationInfo,SG_Callbacks callbacks,class RAS_IRenderTools* rendertools,const struct RAS_LightObject& lightobj, bool glsl, PyTypeObject *T = &Type); virtual ~KX_LightObject(); virtual CValue* GetReplica(); RAS_LightObject* GetLightData() { return &m_lightobj;} @@ -64,6 +64,10 @@ public: void BindShadowBuffer(class RAS_IRasterizer *ras, class KX_Camera *cam, class MT_Transform& camtrans); void UnbindShadowBuffer(class RAS_IRasterizer *ras); void Update(); + + virtual PyObject* py_getattro(PyObject *attr); /* lens, near, far, projection_matrix */ + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *pyvalue); /* attributes */ static PyObject* pyattr_get_color(void* self_v, const KX_PYATTRIBUTE_DEF *attrdef); diff --git a/source/gameengine/Ketsji/KX_MeshProxy.cpp b/source/gameengine/Ketsji/KX_MeshProxy.cpp index 96e8f61e4c8..11effa1ca98 100644 --- a/source/gameengine/Ketsji/KX_MeshProxy.cpp +++ b/source/gameengine/Ketsji/KX_MeshProxy.cpp @@ -62,15 +62,18 @@ PyTypeObject KX_MeshProxy::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_MeshProxy::Parents[] = { + &KX_MeshProxy::Type, &CValue::Type, - 0,0,0,0,0,0, - py_base_new + &PyObjectPlus::Type, + NULL }; PyMethodDef KX_MeshProxy::Methods[] = { @@ -103,8 +106,24 @@ void KX_MeshProxy::SetMeshModified(bool v) m_meshobj->SetMeshModified(v); } + +PyObject* KX_MeshProxy::py_getattro(PyObject *attr) +{ + py_getattro_up(CValue); +} + +PyObject* KX_MeshProxy::py_getattro_dict() { + py_getattro_dict_up(CValue); +} + +int KX_MeshProxy::py_setattro(PyObject *attr, PyObject* value) +{ + py_setattro_up(CValue); +} + + KX_MeshProxy::KX_MeshProxy(RAS_MeshObject* mesh) - : CValue(), m_meshobj(mesh) + : CValue(&Type), m_meshobj(mesh) { } @@ -131,14 +150,14 @@ PyObject* KX_MeshProxy::PyGetNumMaterials(PyObject* args, PyObject* kwds) { int num = m_meshobj->NumMaterials(); ShowDeprecationWarning("getNumMaterials()", "the numMaterials property"); - return PyLong_FromSsize_t(num); + return PyInt_FromLong(num); } PyObject* KX_MeshProxy::PyGetNumPolygons() { int num = m_meshobj->NumPolygons(); ShowDeprecationWarning("getNumPolygons()", "the numPolygons property"); - return PyLong_FromSsize_t(num); + return PyInt_FromLong(num); } PyObject* KX_MeshProxy::PyGetMaterialName(PyObject* args, PyObject* kwds) @@ -154,7 +173,7 @@ PyObject* KX_MeshProxy::PyGetMaterialName(PyObject* args, PyObject* kwds) return NULL; } - return PyUnicode_FromString(matname.Ptr()); + return PyString_FromString(matname.Ptr()); } @@ -172,7 +191,7 @@ PyObject* KX_MeshProxy::PyGetTextureName(PyObject* args, PyObject* kwds) return NULL; } - return PyUnicode_FromString(matname.Ptr()); + return PyString_FromString(matname.Ptr()); } @@ -195,7 +214,7 @@ PyObject* KX_MeshProxy::PyGetVertexArrayLength(PyObject* args, PyObject* kwds) length = m_meshobj->NumVertices(mat); } - return PyLong_FromSsize_t(length); + return PyInt_FromLong(length); } @@ -285,12 +304,12 @@ PyObject* KX_MeshProxy::pyattr_get_materials(void *self_v, const KX_PYATTRIBUTE_ PyObject * KX_MeshProxy::pyattr_get_numMaterials(void * selfv, const KX_PYATTRIBUTE_DEF * attrdef) { KX_MeshProxy * self = static_cast<KX_MeshProxy *> (selfv); - return PyLong_FromSsize_t(self->m_meshobj->NumMaterials()); + return PyInt_FromLong(self->m_meshobj->NumMaterials()); } PyObject * KX_MeshProxy::pyattr_get_numPolygons(void * selfv, const KX_PYATTRIBUTE_DEF * attrdef) { KX_MeshProxy * self = static_cast<KX_MeshProxy *> (selfv); - return PyLong_FromSsize_t(self->m_meshobj->NumPolygons()); + return PyInt_FromLong(self->m_meshobj->NumPolygons()); } /* a close copy of ConvertPythonToGameObject but for meshes */ @@ -313,13 +332,13 @@ bool ConvertPythonToMesh(PyObject * value, RAS_MeshObject **object, bool py_none } } - if (PyUnicode_Check(value)) { - *object = (RAS_MeshObject*)SCA_ILogicBrick::m_sCurrentLogicManager->GetMeshByName(STR_String( _PyUnicode_AsString(value) )); + if (PyString_Check(value)) { + *object = (RAS_MeshObject*)SCA_ILogicBrick::m_sCurrentLogicManager->GetMeshByName(STR_String( PyString_AsString(value) )); if (*object) { return true; } else { - PyErr_Format(PyExc_ValueError, "%s, requested name \"%s\" did not match any KX_MeshProxy in this scene", error_prefix, _PyUnicode_AsString(value)); + PyErr_Format(PyExc_ValueError, "%s, requested name \"%s\" did not match any KX_MeshProxy in this scene", error_prefix, PyString_AsString(value)); return false; } } diff --git a/source/gameengine/Ketsji/KX_MeshProxy.h b/source/gameengine/Ketsji/KX_MeshProxy.h index 4b6543677ad..bfdd4be4118 100644 --- a/source/gameengine/Ketsji/KX_MeshProxy.h +++ b/source/gameengine/Ketsji/KX_MeshProxy.h @@ -56,6 +56,9 @@ public: virtual CValue* GetReplica(); // stuff for python integration + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); KX_PYMETHOD(KX_MeshProxy,GetNumMaterials); // Deprecated KX_PYMETHOD(KX_MeshProxy,GetMaterialName); diff --git a/source/gameengine/Ketsji/KX_MouseFocusSensor.cpp b/source/gameengine/Ketsji/KX_MouseFocusSensor.cpp index ba4b47cb03f..fde10a493db 100644 --- a/source/gameengine/Ketsji/KX_MouseFocusSensor.cpp +++ b/source/gameengine/Ketsji/KX_MouseFocusSensor.cpp @@ -63,8 +63,9 @@ KX_MouseFocusSensor::KX_MouseFocusSensor(SCA_MouseManager* eventmgr, int focusmode, KX_Scene* kxscene, KX_KetsjiEngine *kxengine, - SCA_IObject* gameobj) - : SCA_MouseSensor(eventmgr, startx, starty, mousemode, gameobj), + SCA_IObject* gameobj, + PyTypeObject* T) + : SCA_MouseSensor(eventmgr, startx, starty, mousemode, gameobj, T), m_focusmode(focusmode), m_kxscene(kxscene), m_kxengine(kxengine) @@ -355,15 +356,20 @@ PyTypeObject KX_MouseFocusSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_MouseFocusSensor::Parents[] = { + &KX_MouseFocusSensor::Type, &SCA_MouseSensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ISensor::Type, + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_MouseFocusSensor::Methods[] = { @@ -387,6 +393,15 @@ PyAttributeDef KX_MouseFocusSensor::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_MouseFocusSensor::py_getattro(PyObject *attr) { + py_getattro_up(SCA_MouseSensor); +} + +PyObject* KX_MouseFocusSensor::py_getattro_dict() { + py_getattro_dict_up(SCA_MouseSensor); +} + + const char KX_MouseFocusSensor::GetHitObject_doc[] = "getHitObject()\n" "\tReturns the object that was hit by this ray.\n"; diff --git a/source/gameengine/Ketsji/KX_MouseFocusSensor.h b/source/gameengine/Ketsji/KX_MouseFocusSensor.h index dfada7a59cc..29d674eb305 100644 --- a/source/gameengine/Ketsji/KX_MouseFocusSensor.h +++ b/source/gameengine/Ketsji/KX_MouseFocusSensor.h @@ -56,7 +56,8 @@ class KX_MouseFocusSensor : public SCA_MouseSensor int focusmode, KX_Scene* kxscene, KX_KetsjiEngine* kxengine, - SCA_IObject* gameobj); + SCA_IObject* gameobj, + PyTypeObject* T=&Type ); virtual ~KX_MouseFocusSensor() { ; }; virtual CValue* GetReplica() { @@ -88,6 +89,8 @@ class KX_MouseFocusSensor : public SCA_MouseSensor /* --------------------------------------------------------------------- */ /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); KX_PYMETHOD_DOC_NOARGS(KX_MouseFocusSensor,GetRayTarget); KX_PYMETHOD_DOC_NOARGS(KX_MouseFocusSensor,GetRaySource); diff --git a/source/gameengine/Ketsji/KX_NearSensor.cpp b/source/gameengine/Ketsji/KX_NearSensor.cpp index 1a211a64b35..44842b7f5b3 100644 --- a/source/gameengine/Ketsji/KX_NearSensor.cpp +++ b/source/gameengine/Ketsji/KX_NearSensor.cpp @@ -48,13 +48,15 @@ KX_NearSensor::KX_NearSensor(SCA_EventManager* eventmgr, bool bFindMaterial, const STR_String& touchedpropname, class KX_Scene* scene, - PHY_IPhysicsController* ctrl) + PHY_IPhysicsController* ctrl, + PyTypeObject* T) :KX_TouchSensor(eventmgr, gameobj, bFindMaterial, false, - touchedpropname - /*, scene */), + touchedpropname, + /* scene, */ + T), m_Margin(margin), m_ResetMargin(resetmargin) @@ -270,17 +272,26 @@ PyTypeObject KX_NearSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + + +PyParentObject KX_NearSensor::Parents[] = { + &KX_NearSensor::Type, &KX_TouchSensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ISensor::Type, + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; + + PyMethodDef KX_NearSensor::Methods[] = { //No methods {NULL,NULL} //Sentinel @@ -291,3 +302,18 @@ PyAttributeDef KX_NearSensor::Attributes[] = { KX_PYATTRIBUTE_FLOAT_RW_CHECK("resetDistance", 0, 100, KX_NearSensor, m_ResetMargin, CheckResetDistance), {NULL} //Sentinel }; + + +PyObject* KX_NearSensor::py_getattro(PyObject *attr) +{ + py_getattro_up(KX_TouchSensor); +} + +PyObject* KX_NearSensor::py_getattro_dict() { + py_getattro_dict_up(KX_TouchSensor); +} + +int KX_NearSensor::py_setattro(PyObject*attr, PyObject* value) +{ + py_setattro_up(KX_TouchSensor); +} diff --git a/source/gameengine/Ketsji/KX_NearSensor.h b/source/gameengine/Ketsji/KX_NearSensor.h index f3c1d74805c..63099e181a0 100644 --- a/source/gameengine/Ketsji/KX_NearSensor.h +++ b/source/gameengine/Ketsji/KX_NearSensor.h @@ -54,7 +54,8 @@ public: bool bFindMaterial, const STR_String& touchedpropname, class KX_Scene* scene, - PHY_IPhysicsController* ctrl); + PHY_IPhysicsController* ctrl, + PyTypeObject* T=&Type); /* public: KX_NearSensor(class SCA_EventManager* eventmgr, @@ -63,7 +64,8 @@ public: double resetmargin, bool bFindMaterial, const STR_String& touchedpropname, - class KX_Scene* scene); + class KX_Scene* scene, + PyTypeObject* T=&Type); */ virtual ~KX_NearSensor(); virtual void SynchronizeTransform(); @@ -81,6 +83,9 @@ public: /* --------------------------------------------------------------------- */ /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); //No methods diff --git a/source/gameengine/Ketsji/KX_ObjectActuator.cpp b/source/gameengine/Ketsji/KX_ObjectActuator.cpp index ae340d12be4..eaae04d406d 100644 --- a/source/gameengine/Ketsji/KX_ObjectActuator.cpp +++ b/source/gameengine/Ketsji/KX_ObjectActuator.cpp @@ -53,9 +53,10 @@ KX_ObjectActuator( const MT_Vector3& linV, const MT_Vector3& angV, const short damping, - const KX_LocalFlags& flag + const KX_LocalFlags& flag, + PyTypeObject* T ) : - SCA_IActuator(gameobj), + SCA_IActuator(gameobj,T), m_force(force), m_torque(torque), m_dloc(dloc), @@ -341,15 +342,19 @@ PyTypeObject KX_ObjectActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_ObjectActuator::Parents[] = { + &KX_ObjectActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_ObjectActuator::Methods[] = { @@ -391,14 +396,9 @@ PyAttributeDef KX_ObjectActuator::Attributes[] = { KX_PYATTRIBUTE_BOOL_RW("useLocalDLoc", KX_ObjectActuator, m_bitLocalFlag.DLoc), KX_PYATTRIBUTE_VECTOR_RW_CHECK("dRot", -1000, 1000, false, KX_ObjectActuator, m_drot, PyUpdateFuzzyFlags), KX_PYATTRIBUTE_BOOL_RW("useLocalDRot", KX_ObjectActuator, m_bitLocalFlag.DRot), -#ifdef USE_MATHUTILS - KX_PYATTRIBUTE_RW_FUNCTION("linV", KX_ObjectActuator, pyattr_get_linV, pyattr_set_linV), - KX_PYATTRIBUTE_RW_FUNCTION("angV", KX_ObjectActuator, pyattr_get_angV, pyattr_set_angV), -#else KX_PYATTRIBUTE_VECTOR_RW_CHECK("linV", -1000, 1000, false, KX_ObjectActuator, m_linear_velocity, PyUpdateFuzzyFlags), - KX_PYATTRIBUTE_VECTOR_RW_CHECK("angV", -1000, 1000, false, KX_ObjectActuator, m_angular_velocity, PyUpdateFuzzyFlags), -#endif KX_PYATTRIBUTE_BOOL_RW("useLocalLinV", KX_ObjectActuator, m_bitLocalFlag.LinearVelocity), + KX_PYATTRIBUTE_VECTOR_RW_CHECK("angV", -1000, 1000, false, KX_ObjectActuator, m_angular_velocity, PyUpdateFuzzyFlags), KX_PYATTRIBUTE_BOOL_RW("useLocalAngV", KX_ObjectActuator, m_bitLocalFlag.AngularVelocity), KX_PYATTRIBUTE_SHORT_RW("damping", 0, 1000, false, KX_ObjectActuator, m_damping), KX_PYATTRIBUTE_RW_FUNCTION("forceLimitX", KX_ObjectActuator, pyattr_get_forceLimitX, pyattr_set_forceLimitX), @@ -409,130 +409,21 @@ PyAttributeDef KX_ObjectActuator::Attributes[] = { { NULL } //Sentinel }; -/* Attribute get/set functions */ - -#ifdef USE_MATHUTILS - -/* These require an SGNode */ -#define MATHUTILS_VEC_CB_LINV 1 -#define MATHUTILS_VEC_CB_ANGV 2 - -static int mathutils_kxobactu_vector_cb_index= -1; /* index for our callbacks */ - -static int mathutils_obactu_generic_check(PyObject *self_v) -{ - KX_ObjectActuator* self= static_cast<KX_ObjectActuator*>BGE_PROXY_REF(self_v); - if(self==NULL) - return 0; - - return 1; -} - -static int mathutils_obactu_vector_get(PyObject *self_v, int subtype, float *vec_from) -{ - KX_ObjectActuator* self= static_cast<KX_ObjectActuator*>BGE_PROXY_REF(self_v); - if(self==NULL) - return 0; - - switch(subtype) { - case MATHUTILS_VEC_CB_LINV: - self->m_linear_velocity.getValue(vec_from); - break; - case MATHUTILS_VEC_CB_ANGV: - self->m_angular_velocity.getValue(vec_from); - break; - } - - return 1; -} - -static int mathutils_obactu_vector_set(PyObject *self_v, int subtype, float *vec_to) -{ - KX_ObjectActuator* self= static_cast<KX_ObjectActuator*>BGE_PROXY_REF(self_v); - if(self==NULL) - return 0; - - switch(subtype) { - case MATHUTILS_VEC_CB_LINV: - self->m_linear_velocity.setValue(vec_to); - break; - case MATHUTILS_VEC_CB_ANGV: - self->m_angular_velocity.setValue(vec_to); - break; - } - - return 1; -} - -static int mathutils_obactu_vector_get_index(PyObject *self_v, int subtype, float *vec_from, int index) -{ - float f[4]; - /* lazy, avoid repeteing the case statement */ - if(!mathutils_obactu_vector_get(self_v, subtype, f)) - return 0; - - vec_from[index]= f[index]; - return 1; -} - -static int mathutils_obactu_vector_set_index(PyObject *self_v, int subtype, float *vec_to, int index) -{ - float f= vec_to[index]; - - /* lazy, avoid repeteing the case statement */ - if(!mathutils_obactu_vector_get(self_v, subtype, vec_to)) - return 0; - - vec_to[index]= f; - mathutils_obactu_vector_set(self_v, subtype, vec_to); - - return 1; -} - -Mathutils_Callback mathutils_obactu_vector_cb = { - mathutils_obactu_generic_check, - mathutils_obactu_vector_get, - mathutils_obactu_vector_set, - mathutils_obactu_vector_get_index, - mathutils_obactu_vector_set_index -}; - -PyObject* KX_ObjectActuator::pyattr_get_linV(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) -{ - return newVectorObject_cb((PyObject *)self_v, 3, mathutils_kxobactu_vector_cb_index, MATHUTILS_VEC_CB_LINV); +PyObject* KX_ObjectActuator::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IActuator); } -int KX_ObjectActuator::pyattr_set_linV(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) -{ - KX_ObjectActuator* self= static_cast<KX_ObjectActuator*>(self_v); - if (!PyVecTo(value, self->m_linear_velocity)) - return PY_SET_ATTR_FAIL; - - return PY_SET_ATTR_SUCCESS; -} - -PyObject* KX_ObjectActuator::pyattr_get_angV(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) -{ - return newVectorObject_cb((PyObject *)self_v, 3, mathutils_kxobactu_vector_cb_index, MATHUTILS_VEC_CB_ANGV); -} - -int KX_ObjectActuator::pyattr_set_angV(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value) -{ - KX_ObjectActuator* self= static_cast<KX_ObjectActuator*>(self_v); - if (!PyVecTo(value, self->m_angular_velocity)) - return PY_SET_ATTR_FAIL; - return PY_SET_ATTR_SUCCESS; +PyObject* KX_ObjectActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); } - -void KX_ObjectActuator_Mathutils_Callback_Init(void) +int KX_ObjectActuator::py_setattro(PyObject *attr, PyObject *value) { - // register mathutils callbacks, ok to run more then once. - mathutils_kxobactu_vector_cb_index= Mathutils_RegisterCallback(&mathutils_obactu_vector_cb); + py_setattro_up(SCA_IActuator); } -#endif // USE_MATHUTILS +/* Attribute get/set functions */ PyObject* KX_ObjectActuator::pyattr_get_forceLimitX(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { @@ -555,7 +446,7 @@ int KX_ObjectActuator::pyattr_set_forceLimitX(void *self_v, const KX_PYATTRIBUTE { self->m_drot[0] = PyFloat_AsDouble(PySequence_Fast_GET_ITEM(value, 0)); self->m_dloc[0] = PyFloat_AsDouble(PySequence_Fast_GET_ITEM(value, 1)); - self->m_bitLocalFlag.Torque = (PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 2)) != 0); + self->m_bitLocalFlag.Torque = (PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 2)) != 0); if (!PyErr_Occurred()) { @@ -591,7 +482,7 @@ int KX_ObjectActuator::pyattr_set_forceLimitY(void *self_v, const KX_PYATTRIBUTE { self->m_drot[1] = PyFloat_AsDouble(PySequence_Fast_GET_ITEM(value, 0)); self->m_dloc[1] = PyFloat_AsDouble(PySequence_Fast_GET_ITEM(value, 1)); - self->m_bitLocalFlag.DLoc = (PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 2)) != 0); + self->m_bitLocalFlag.DLoc = (PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 2)) != 0); if (!PyErr_Occurred()) { @@ -627,7 +518,7 @@ int KX_ObjectActuator::pyattr_set_forceLimitZ(void *self_v, const KX_PYATTRIBUTE { self->m_drot[2] = PyFloat_AsDouble(PySequence_Fast_GET_ITEM(value, 0)); self->m_dloc[2] = PyFloat_AsDouble(PySequence_Fast_GET_ITEM(value, 1)); - self->m_bitLocalFlag.DRot = (PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 2)) != 0); + self->m_bitLocalFlag.DRot = (PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 2)) != 0); if (!PyErr_Occurred()) { diff --git a/source/gameengine/Ketsji/KX_ObjectActuator.h b/source/gameengine/Ketsji/KX_ObjectActuator.h index 20aec9e0e86..f9bd2a0c748 100644 --- a/source/gameengine/Ketsji/KX_ObjectActuator.h +++ b/source/gameengine/Ketsji/KX_ObjectActuator.h @@ -35,10 +35,6 @@ #include "SCA_IActuator.h" #include "MT_Vector3.h" -#ifdef USE_MATHUTILS -void KX_ObjectActuator_Mathutils_Callback_Init(void); -#endif - class KX_GameObject; // @@ -135,7 +131,8 @@ public: const MT_Vector3& linV, const MT_Vector3& angV, const short damping, - const KX_LocalFlags& flag + const KX_LocalFlags& flag, + PyTypeObject* T=&Type ); ~KX_ObjectActuator(); CValue* GetReplica(); @@ -162,6 +159,10 @@ public: /* --------------------------------------------------------------------- */ /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); KX_PYMETHOD_NOARGS(KX_ObjectActuator,GetForce); KX_PYMETHOD_VARARGS(KX_ObjectActuator,SetForce); @@ -196,13 +197,6 @@ public: static PyObject* pyattr_get_reference(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef); static int pyattr_set_reference(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value); -#ifdef USE_MATHUTILS - static PyObject* pyattr_get_linV(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef); - static int pyattr_set_linV(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value); - static PyObject* pyattr_get_angV(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef); - static int pyattr_set_angV(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value); -#endif - // This lets the attribute macros use UpdateFuzzyFlags() static int PyUpdateFuzzyFlags(void *self, const PyAttributeDef *attrdef) { diff --git a/source/gameengine/Ketsji/KX_OdePhysicsController.cpp b/source/gameengine/Ketsji/KX_OdePhysicsController.cpp new file mode 100644 index 00000000000..dc6990267d4 --- /dev/null +++ b/source/gameengine/Ketsji/KX_OdePhysicsController.cpp @@ -0,0 +1,257 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * The contents of this file may be used under the terms of either the GNU + * General Public License Version 2 or later (the "GPL", see + * http://www.gnu.org/licenses/gpl.html ), or the Blender License 1.0 or + * later (the "BL", see http://www.blender.org/BL/ ) which has to be + * bought from the Blender Foundation to become active, in which case the + * above mentioned GPL option does not apply. + * + * The Original Code is Copyright (C) 2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#include "KX_ConvertPhysicsObject.h" + +#ifdef USE_ODE + +#include "KX_OdePhysicsController.h" +#include "KX_GameObject.h" +#include "KX_MotionState.h" + +#include "MT_assert.h" + +#include "PHY_IPhysicsEnvironment.h" + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +KX_OdePhysicsController::KX_OdePhysicsController( + bool dyna, + bool fullRigidBody, + bool phantom, + class PHY_IMotionState* motionstate, + struct dxSpace* space, + struct dxWorld* world, + float mass, + float friction, + float restitution, + bool implicitsphere, + float center[3], + float extends[3], + float radius + ) +: KX_IPhysicsController(dyna,false,(PHY_IPhysicsController*)this), +ODEPhysicsController( +dyna,fullRigidBody,phantom,motionstate, +space,world,mass,friction,restitution, +implicitsphere,center,extends,radius) +{ +}; + + +bool KX_OdePhysicsController::Update(double time) +{ + return SynchronizeMotionStates(time); +} + +void KX_OdePhysicsController::SetObject (SG_IObject* object) +{ + SG_Controller::SetObject(object); + + // cheating here... + KX_GameObject* gameobj = (KX_GameObject*) object->GetSGClientObject(); + gameobj->SetPhysicsController(this); + +} + + + +void KX_OdePhysicsController::applyImpulse(const MT_Point3& attach, const MT_Vector3& impulse) +{ + ODEPhysicsController::applyImpulse(attach[0],attach[1],attach[2],impulse[0],impulse[1],impulse[2]); +} + + + +void KX_OdePhysicsController::RelativeTranslate(const MT_Vector3& dloc,bool local) +{ + ODEPhysicsController::RelativeTranslate(dloc[0],dloc[1],dloc[2],local); + +} +void KX_OdePhysicsController::RelativeRotate(const MT_Matrix3x3& drot,bool local) +{ + double oldmat[12]; + drot.getValue(oldmat); + float newmat[9]; + float *m = &newmat[0]; + double *orgm = &oldmat[0]; + + *m++ = *orgm++;*m++ = *orgm++;*m++ = *orgm++;orgm++; + *m++ = *orgm++;*m++ = *orgm++;*m++ = *orgm++;orgm++; + *m++ = *orgm++;*m++ = *orgm++;*m++ = *orgm++;orgm++; + + ODEPhysicsController::RelativeRotate(newmat,local); + +} + +void KX_OdePhysicsController::ApplyTorque(const MT_Vector3& torque,bool local) +{ + ODEPhysicsController::ApplyTorque(torque[0],torque[1],torque[2],local); + +} +void KX_OdePhysicsController::ApplyForce(const MT_Vector3& force,bool local) +{ + ODEPhysicsController::ApplyForce(force[0],force[1],force[2],local); + +} +MT_Vector3 KX_OdePhysicsController::GetLinearVelocity() +{ + return MT_Vector3(0,0,0); +} + +MT_Vector3 KX_OdePhysicsController::GetVelocity(const MT_Point3& pos) +{ + return MT_Vector3(0,0,0); +} + +void KX_OdePhysicsController::SetAngularVelocity(const MT_Vector3& ang_vel,bool local) +{ + +} +void KX_OdePhysicsController::SetLinearVelocity(const MT_Vector3& lin_vel,bool local) +{ + ODEPhysicsController::SetLinearVelocity(lin_vel[0],lin_vel[1],lin_vel[2],local); +} + +void KX_OdePhysicsController::setOrientation(const MT_Matrix3x3& rot) +{ + MT_Quaternion orn = rot.getRotation(); + ODEPhysicsController::setOrientation(orn[0],orn[1],orn[2],orn[3]); +} + +void KX_OdePhysicsController::getOrientation(MT_Quaternion& orn) +{ + float florn[4]; + florn[0]=orn[0]; + florn[1]=orn[1]; + florn[2]=orn[2]; + florn[3]=orn[3]; + ODEPhysicsController::getOrientation(florn[0],florn[1],florn[2],florn[3]); + orn[0] = florn[0]; + orn[1] = florn[1]; + orn[2] = florn[2]; + orn[3] = florn[3]; + + +} + +void KX_OdePhysicsController::setPosition(const MT_Point3& pos) +{ + ODEPhysicsController::setPosition(pos[0],pos[1],pos[2]); +} + +void KX_OdePhysicsController::setScaling(const MT_Vector3& scaling) +{ +} + +MT_Scalar KX_OdePhysicsController::GetMass() +{ + return ODEPhysicsController::getMass(); +} + +MT_Scalar KX_OdePhysicsController::GetRadius() +{ + return MT_Scalar(0.f); +} + +MT_Vector3 KX_OdePhysicsController::getReactionForce() +{ + return MT_Vector3(0,0,0); +} +void KX_OdePhysicsController::setRigidBody(bool rigid) +{ + +} + +void KX_OdePhysicsController::SuspendDynamics(bool) +{ + ODEPhysicsController::SuspendDynamics(); +} +void KX_OdePhysicsController::RestoreDynamics() +{ + ODEPhysicsController::RestoreDynamics(); +} + + +SG_Controller* KX_OdePhysicsController::GetReplica(class SG_Node* destnode) +{ + PHY_IMotionState* motionstate = new KX_MotionState(destnode); + KX_OdePhysicsController* copyctrl = new KX_OdePhysicsController(*this); + + // nlin: copied from KX_SumoPhysicsController.cpp. Not 100% sure what this does.... + // furthermore, the parentctrl is not used in ODEPhysicsController::PostProcessReplica, but + // maybe it can/should be used in the future... + + // begin copy block ------------------------------------------------------------------ + + //parentcontroller is here be able to avoid collisions between parent/child + + PHY_IPhysicsController* parentctrl = NULL; + + if (destnode != destnode->GetRootSGParent()) + { + KX_GameObject* clientgameobj = (KX_GameObject*) destnode->GetRootSGParent()->GetSGClientObject(); + if (clientgameobj) + { + parentctrl = (KX_OdePhysicsController*)clientgameobj->GetPhysicsController(); + } else + { + // it could be a false node, try the children + NodeList::const_iterator childit; + for ( + childit = destnode->GetSGChildren().begin(); + childit!= destnode->GetSGChildren().end(); + ++childit + ) { + KX_GameObject* clientgameobj = static_cast<KX_GameObject*>( (*childit)->GetSGClientObject()); + if (clientgameobj) + { + parentctrl = (KX_OdePhysicsController*)clientgameobj->GetPhysicsController(); + } + } + } + } + // end copy block ------------------------------------------------------------------ + + copyctrl->PostProcessReplica(motionstate, this); + + return copyctrl; + +} + +void KX_OdePhysicsController::resolveCombinedVelocities(float linvelX,float linvelY,float linvelZ,float angVelX,float angVelY,float angVelZ) +{ +} + + +void KX_OdePhysicsController::SetSumoTransform(bool nondynaonly) +{ + +} + // todo: remove next line ! +void KX_OdePhysicsController::SetSimulatedTime(double time) +{ + +} + +#endif //USE_ODE diff --git a/source/gameengine/Ketsji/KX_OdePhysicsController.h b/source/gameengine/Ketsji/KX_OdePhysicsController.h new file mode 100644 index 00000000000..8c3974c38a3 --- /dev/null +++ b/source/gameengine/Ketsji/KX_OdePhysicsController.h @@ -0,0 +1,109 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * The contents of this file may be used under the terms of either the GNU + * General Public License Version 2 or later (the "GPL", see + * http://www.gnu.org/licenses/gpl.html ), or the Blender License 1.0 or + * later (the "BL", see http://www.blender.org/BL/ ) which has to be + * bought from the Blender Foundation to become active, in which case the + * above mentioned GPL option does not apply. + * + * The Original Code is Copyright (C) 2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef __KX_ODEPHYSICSCONTROLLER_H +#define __KX_ODEPHYSICSCONTROLLER_H + +#include "KX_IPhysicsController.h" +#include "OdePhysicsController.h" + +/** + Physics Controller, a special kind of Scene Graph Transformation Controller. + It get's callbacks from Physics in case a transformation change took place. + Each time the scene graph get's updated, the controller get's a chance + in the 'Update' method to reflect changed. +*/ + +class KX_OdePhysicsController : public KX_IPhysicsController, public ODEPhysicsController + +{ + +public: + KX_OdePhysicsController( + bool dyna, + bool fullRigidBody, + bool phantom, + class PHY_IMotionState* motionstate, + struct dxSpace* space, + struct dxWorld* world, + float mass, + float friction, + float restitution, + bool implicitsphere, + float center[3], + float extends[3], + float radius); + + virtual ~KX_OdePhysicsController() {}; + + virtual void applyImpulse(const MT_Point3& attach, const MT_Vector3& impulse); + virtual void SetObject (SG_IObject* object); + + virtual void RelativeTranslate(const MT_Vector3& dloc,bool local); + virtual void RelativeRotate(const MT_Matrix3x3& drot,bool local); + virtual void ApplyTorque(const MT_Vector3& torque,bool local); + virtual void ApplyForce(const MT_Vector3& force,bool local); + virtual MT_Vector3 GetLinearVelocity(); + virtual MT_Vector3 GetVelocity(const MT_Point3& pos); + virtual void SetAngularVelocity(const MT_Vector3& ang_vel,bool local); + virtual void SetLinearVelocity(const MT_Vector3& lin_vel,bool local); + virtual void resolveCombinedVelocities(float linvelX,float linvelY,float linvelZ,float angVelX,float angVelY,float angVelZ); + virtual void getOrientation(MT_Quaternion& orn); + virtual void setOrientation(const MT_Matrix3x3& orn); + virtual void setPosition(const MT_Point3& pos); + virtual void setScaling(const MT_Vector3& scaling); + virtual void SetTransform() {} + virtual MT_Scalar GetMass(); + virtual MT_Vector3 getReactionForce(); + virtual void setRigidBody(bool rigid); + virtual void AddCompoundChild(KX_IPhysicsController* child) { } + virtual void RemoveCompoundChild(KX_IPhysicsController* child) { } + + virtual void SuspendDynamics(bool); + virtual void RestoreDynamics(); + virtual MT_Scalar GetRadius(); + + virtual SG_Controller* GetReplica(class SG_Node* destnode); + + virtual float GetLinVelocityMin() { return ODEPhysicsController::GetLinVelocityMin(); } + virtual void SetLinVelocityMin(float val) { ODEPhysicsController::SetLinVelocityMin(val); } + virtual float GetLinVelocityMax() { return ODEPhysicsController::GetLinVelocityMax(); } + virtual void SetLinVelocityMax(float val) { ODEPhysicsController::SetLinVelocityMax(val); } + + virtual void SetSumoTransform(bool nondynaonly); + // todo: remove next line ! + virtual void SetSimulatedTime(double time); + + // call from scene graph to update + virtual bool Update(double time); + + void + SetOption( + int option, + int value + ){ + // intentionally empty + }; + +}; + +#endif //__KX_ODEPHYSICSCONTROLLER_H + diff --git a/source/gameengine/Ketsji/KX_ParentActuator.cpp b/source/gameengine/Ketsji/KX_ParentActuator.cpp index befa2aaff56..cd2ed456c48 100644 --- a/source/gameengine/Ketsji/KX_ParentActuator.cpp +++ b/source/gameengine/Ketsji/KX_ParentActuator.cpp @@ -50,8 +50,9 @@ KX_ParentActuator::KX_ParentActuator(SCA_IObject *gameobj, int mode, bool addToCompound, bool ghost, - SCA_IObject *ob) - : SCA_IActuator(gameobj), + SCA_IObject *ob, + PyTypeObject* T) + : SCA_IActuator(gameobj, T), m_mode(mode), m_addToCompound(addToCompound), m_ghost(ghost), @@ -156,15 +157,19 @@ PyTypeObject KX_ParentActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_ParentActuator::Parents[] = { + &KX_ParentActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_ParentActuator::Methods[] = { @@ -212,6 +217,18 @@ int KX_ParentActuator::pyattr_set_object(void *self, const struct KX_PYATTRIBUTE } +PyObject* KX_ParentActuator::py_getattro(PyObject *attr) { + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_ParentActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_ParentActuator::py_setattro(PyObject *attr, PyObject* value) { + py_setattro_up(SCA_IActuator); +} + /* Deprecated -----> */ /* 1. setObject */ const char KX_ParentActuator::SetObject_doc[] = @@ -256,7 +273,7 @@ PyObject* KX_ParentActuator::PyGetObject(PyObject* args) Py_RETURN_NONE; if (ret_name_only) - return PyUnicode_FromString(m_ob->GetName().ReadPtr()); + return PyString_FromString(m_ob->GetName().ReadPtr()); else return m_ob->GetProxy(); } diff --git a/source/gameengine/Ketsji/KX_ParentActuator.h b/source/gameengine/Ketsji/KX_ParentActuator.h index aeb39eabf89..148375e994c 100644 --- a/source/gameengine/Ketsji/KX_ParentActuator.h +++ b/source/gameengine/Ketsji/KX_ParentActuator.h @@ -68,7 +68,8 @@ class KX_ParentActuator : public SCA_IActuator int mode, bool addToCompound, bool ghost, - SCA_IObject *ob); + SCA_IObject *ob, + PyTypeObject* T=&Type); virtual ~KX_ParentActuator(); virtual bool Update(); @@ -81,6 +82,10 @@ class KX_ParentActuator : public SCA_IActuator /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); + /* These are used to get and set m_ob */ static PyObject* pyattr_get_object(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef); static int pyattr_set_object(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value); diff --git a/source/gameengine/Ketsji/KX_PhysicsObjectWrapper.cpp b/source/gameengine/Ketsji/KX_PhysicsObjectWrapper.cpp index 7bce311f1b6..c968e50957e 100644 --- a/source/gameengine/Ketsji/KX_PhysicsObjectWrapper.cpp +++ b/source/gameengine/Ketsji/KX_PhysicsObjectWrapper.cpp @@ -39,8 +39,8 @@ KX_PhysicsObjectWrapper::KX_PhysicsObjectWrapper( PHY_IPhysicsController* ctrl, - PHY_IPhysicsEnvironment* physenv) : - PyObjectPlus(), + PHY_IPhysicsEnvironment* physenv,PyTypeObject *T) : + PyObjectPlus(T), m_ctrl(ctrl), m_physenv(physenv) { @@ -129,17 +129,46 @@ PyTypeObject KX_PhysicsObjectWrapper::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &PyObjectPlus::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods +}; + +PyParentObject KX_PhysicsObjectWrapper::Parents[] = { + &KX_PhysicsObjectWrapper::Type, + NULL +}; + +PyObject* KX_PhysicsObjectWrapper::py_getattro(PyObject *attr) +{ + py_getattro_up(PyObjectPlus); +} + +PyObject* KX_PhysicsObjectWrapper::py_getattro_dict() { + py_getattro_dict_up(PyObjectPlus); +} + +int KX_PhysicsObjectWrapper::py_setattro(PyObject *attr,PyObject *pyobj) +{ + int result = 1; + + if (PyInt_Check(pyobj)) + { + result = 0; + } + if (PyString_Check(pyobj)) + { + result = 0; + } + if (result) + result = PyObjectPlus::py_setattro(attr,pyobj); + + return result; }; + PyMethodDef KX_PhysicsObjectWrapper::Methods[] = { {"setPosition",(PyCFunction) KX_PhysicsObjectWrapper::sPySetPosition, METH_VARARGS}, {"setLinearVelocity",(PyCFunction) KX_PhysicsObjectWrapper::sPySetLinearVelocity, METH_VARARGS}, diff --git a/source/gameengine/Ketsji/KX_PhysicsObjectWrapper.h b/source/gameengine/Ketsji/KX_PhysicsObjectWrapper.h index fa6fd1d1f2a..1b59686babc 100644 --- a/source/gameengine/Ketsji/KX_PhysicsObjectWrapper.h +++ b/source/gameengine/Ketsji/KX_PhysicsObjectWrapper.h @@ -35,8 +35,12 @@ class KX_PhysicsObjectWrapper : public PyObjectPlus { Py_Header; + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); public: - KX_PhysicsObjectWrapper(class PHY_IPhysicsController* ctrl,class PHY_IPhysicsEnvironment* physenv); + KX_PhysicsObjectWrapper(class PHY_IPhysicsController* ctrl,class PHY_IPhysicsEnvironment* physenv,PyTypeObject *T = &Type); virtual ~KX_PhysicsObjectWrapper(); KX_PYMETHOD_VARARGS(KX_PhysicsObjectWrapper,SetPosition); diff --git a/source/gameengine/Ketsji/KX_PolyProxy.cpp b/source/gameengine/Ketsji/KX_PolyProxy.cpp index a1571b17756..b56b5500c39 100644 --- a/source/gameengine/Ketsji/KX_PolyProxy.cpp +++ b/source/gameengine/Ketsji/KX_PolyProxy.cpp @@ -55,15 +55,18 @@ PyTypeObject KX_PolyProxy::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_PolyProxy::Parents[] = { + &KX_PolyProxy::Type, &CValue::Type, - 0,0,0,0,0,0, - py_base_new + &PyObjectPlus::Type, + NULL }; PyMethodDef KX_PolyProxy::Methods[] = { @@ -95,17 +98,16 @@ PyAttributeDef KX_PolyProxy::Attributes[] = { { NULL } //Sentinel }; -#if 0 PyObject* KX_PolyProxy::py_getattro(PyObject *attr) { - char *attr_str= _PyUnicode_AsString(attr); + char *attr_str= PyString_AsString(attr); if (!strcmp(attr_str, "matname")) { - return PyUnicode_FromString(m_polygon->GetMaterial()->GetPolyMaterial()->GetMaterialName()); + return PyString_FromString(m_polygon->GetMaterial()->GetPolyMaterial()->GetMaterialName()); } if (!strcmp(attr_str, "texture")) { - return PyUnicode_FromString(m_polygon->GetMaterial()->GetPolyMaterial()->GetTextureName()); + return PyString_FromString(m_polygon->GetMaterial()->GetPolyMaterial()->GetTextureName()); } if (!strcmp(attr_str, "material")) { @@ -134,35 +136,38 @@ PyObject* KX_PolyProxy::py_getattro(PyObject *attr) // found it break; } - return PyLong_FromSsize_t(matid); + return PyInt_FromLong(matid); } if (!strcmp(attr_str, "v1")) { - return PyLong_FromSsize_t(m_polygon->GetVertexOffset(0)); + return PyInt_FromLong(m_polygon->GetVertexOffset(0)); } if (!strcmp(attr_str, "v2")) { - return PyLong_FromSsize_t(m_polygon->GetVertexOffset(1)); + return PyInt_FromLong(m_polygon->GetVertexOffset(1)); } if (!strcmp(attr_str, "v3")) { - return PyLong_FromSsize_t(m_polygon->GetVertexOffset(2)); + return PyInt_FromLong(m_polygon->GetVertexOffset(2)); } if (!strcmp(attr_str, "v4")) { - return PyLong_FromSsize_t(((m_polygon->VertexCount()>3)?m_polygon->GetVertexOffset(3):0)); + return PyInt_FromLong(((m_polygon->VertexCount()>3)?m_polygon->GetVertexOffset(3):0)); } if (!strcmp(attr_str, "visible")) { - return PyLong_FromSsize_t(m_polygon->IsVisible()); + return PyInt_FromLong(m_polygon->IsVisible()); } if (!strcmp(attr_str, "collide")) { - return PyLong_FromSsize_t(m_polygon->IsCollider()); + return PyInt_FromLong(m_polygon->IsCollider()); } - // py_getattro_up(CValue); // XXX -- todo, make all these attributes + py_getattro_up(CValue); +} + +PyObject* KX_PolyProxy::py_getattro_dict() { + py_getattro_dict_up(CValue); } -#endif KX_PolyProxy::KX_PolyProxy(const RAS_MeshObject*mesh, RAS_Polygon* polygon) : m_polygon(polygon), @@ -199,37 +204,37 @@ KX_PYMETHODDEF_DOC_NOARGS(KX_PolyProxy, getMaterialIndex, // found it break; } - return PyLong_FromSsize_t(matid); + return PyInt_FromLong(matid); } KX_PYMETHODDEF_DOC_NOARGS(KX_PolyProxy, getNumVertex, "getNumVertex() : returns the number of vertex of the polygon, 3 or 4\n") { - return PyLong_FromSsize_t(m_polygon->VertexCount()); + return PyInt_FromLong(m_polygon->VertexCount()); } KX_PYMETHODDEF_DOC_NOARGS(KX_PolyProxy, isVisible, "isVisible() : returns whether the polygon is visible or not\n") { - return PyLong_FromSsize_t(m_polygon->IsVisible()); + return PyInt_FromLong(m_polygon->IsVisible()); } KX_PYMETHODDEF_DOC_NOARGS(KX_PolyProxy, isCollider, "isCollider() : returns whether the polygon is receives collision or not\n") { - return PyLong_FromSsize_t(m_polygon->IsCollider()); + return PyInt_FromLong(m_polygon->IsCollider()); } KX_PYMETHODDEF_DOC_NOARGS(KX_PolyProxy, getMaterialName, "getMaterialName() : returns the polygon material name, \"NoMaterial\" if no material\n") { - return PyUnicode_FromString(m_polygon->GetMaterial()->GetPolyMaterial()->GetMaterialName()); + return PyString_FromString(m_polygon->GetMaterial()->GetPolyMaterial()->GetMaterialName()); } KX_PYMETHODDEF_DOC_NOARGS(KX_PolyProxy, getTextureName, "getTexturelName() : returns the polygon texture name, \"NULL\" if no texture\n") { - return PyUnicode_FromString(m_polygon->GetMaterial()->GetPolyMaterial()->GetTextureName()); + return PyString_FromString(m_polygon->GetMaterial()->GetPolyMaterial()->GetTextureName()); } KX_PYMETHODDEF_DOC(KX_PolyProxy, getVertexIndex, @@ -250,9 +255,9 @@ KX_PYMETHODDEF_DOC(KX_PolyProxy, getVertexIndex, } if (index < m_polygon->VertexCount()) { - return PyLong_FromSsize_t(m_polygon->GetVertexOffset(index)); + return PyInt_FromLong(m_polygon->GetVertexOffset(index)); } - return PyLong_FromSsize_t(0); + return PyInt_FromLong(0); } KX_PYMETHODDEF_DOC_NOARGS(KX_PolyProxy, getMesh, diff --git a/source/gameengine/Ketsji/KX_PolyProxy.h b/source/gameengine/Ketsji/KX_PolyProxy.h index e619617d312..d8fd36fec6c 100644 --- a/source/gameengine/Ketsji/KX_PolyProxy.h +++ b/source/gameengine/Ketsji/KX_PolyProxy.h @@ -52,6 +52,8 @@ public: // stuff for python integration + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); KX_PYMETHOD_DOC_NOARGS(KX_PolyProxy,getMaterialIndex) KX_PYMETHOD_DOC_NOARGS(KX_PolyProxy,getNumVertex) diff --git a/source/gameengine/Ketsji/KX_PolygonMaterial.cpp b/source/gameengine/Ketsji/KX_PolygonMaterial.cpp index 9bc84127572..506c167a905 100644 --- a/source/gameengine/Ketsji/KX_PolygonMaterial.cpp +++ b/source/gameengine/Ketsji/KX_PolygonMaterial.cpp @@ -51,8 +51,8 @@ #include "KX_PyMath.h" -KX_PolygonMaterial::KX_PolygonMaterial() - : PyObjectPlus(), +KX_PolygonMaterial::KX_PolygonMaterial(PyTypeObject *T) + : PyObjectPlus(T), RAS_IPolyMaterial(), m_tface(NULL), @@ -115,7 +115,7 @@ bool KX_PolygonMaterial::Activate(RAS_IRasterizer* rasty, TCachingInfo& cachingI PyObject *ret = PyObject_CallMethod(m_pymaterial, "activate", "(NNO)", pyRasty, pyCachingInfo, (PyObject*) this->m_proxy); if (ret) { - bool value = PyLong_AsSsize_t(ret); + bool value = PyInt_AsLong(ret); Py_DECREF(ret); dopass = value; } @@ -255,17 +255,33 @@ PyTypeObject KX_PolygonMaterial::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &PyObjectPlus::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods }; +PyParentObject KX_PolygonMaterial::Parents[] = { + &KX_PolygonMaterial::Type, + &PyObjectPlus::Type, + NULL +}; + +PyObject* KX_PolygonMaterial::py_getattro(PyObject *attr) +{ + py_getattro_up(PyObjectPlus); +} + +PyObject* KX_PolygonMaterial::py_getattro_dict() { + py_getattro_dict_up(PyObjectPlus); +} + +int KX_PolygonMaterial::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(PyObjectPlus); +} + KX_PYMETHODDEF_DOC(KX_PolygonMaterial, setCustomMaterial, "setCustomMaterial(material)") { PyObject *material; @@ -331,13 +347,13 @@ KX_PYMETHODDEF_DOC(KX_PolygonMaterial, activate, "activate(rasty, cachingInfo)") PyObject* KX_PolygonMaterial::pyattr_get_texture(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_PolygonMaterial* self= static_cast<KX_PolygonMaterial*>(self_v); - return PyUnicode_FromString(self->m_texturename.ReadPtr()); + return PyString_FromString(self->m_texturename.ReadPtr()); } PyObject* KX_PolygonMaterial::pyattr_get_material(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_PolygonMaterial* self= static_cast<KX_PolygonMaterial*>(self_v); - return PyUnicode_FromString(self->m_materialname.ReadPtr()); + return PyString_FromString(self->m_materialname.ReadPtr()); } /* this does not seem useful */ @@ -354,7 +370,7 @@ PyObject* KX_PolygonMaterial::pyattr_get_gl_texture(void *self_v, const KX_PYATT if (self->m_tface && self->m_tface->tpage) bindcode= self->m_tface->tpage->bindcode; - return PyLong_FromSsize_t(bindcode); + return PyInt_FromLong(bindcode); } diff --git a/source/gameengine/Ketsji/KX_PolygonMaterial.h b/source/gameengine/Ketsji/KX_PolygonMaterial.h index 266b4d7e789..89ecb026da9 100644 --- a/source/gameengine/Ketsji/KX_PolygonMaterial.h +++ b/source/gameengine/Ketsji/KX_PolygonMaterial.h @@ -57,7 +57,7 @@ private: mutable int m_pass; public: - KX_PolygonMaterial(); + KX_PolygonMaterial(PyTypeObject *T = &Type); void Initialize(const STR_String &texname, Material* ma, int materialindex, @@ -116,7 +116,10 @@ public: KX_PYMETHOD_DOC(KX_PolygonMaterial, setCustomMaterial); KX_PYMETHOD_DOC(KX_PolygonMaterial, loadProgram); - virtual PyObject* py_repr(void) { return PyUnicode_FromString(m_material ? ((ID *)m_material)->name+2 : ""); } + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *pyvalue); + virtual PyObject* py_repr(void) { return PyString_FromString(m_material ? ((ID *)m_material)->name+2 : ""); } static PyObject* pyattr_get_texture(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef); static PyObject* pyattr_get_material(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef); diff --git a/source/gameengine/Ketsji/KX_PyConstraintBinding.cpp b/source/gameengine/Ketsji/KX_PyConstraintBinding.cpp index 94e8d1fd583..4ec901a2f5e 100644 --- a/source/gameengine/Ketsji/KX_PyConstraintBinding.cpp +++ b/source/gameengine/Ketsji/KX_PyConstraintBinding.cpp @@ -640,7 +640,7 @@ PyObject* initPythonConstraintBinding() // Add some symbolic constants to the module d = PyModule_GetDict(m); - ErrorObject = PyUnicode_FromString("PhysicsConstraints.error"); + ErrorObject = PyString_FromString("PhysicsConstraints.error"); PyDict_SetItemString(d, "error", ErrorObject); Py_DECREF(ErrorObject); diff --git a/source/gameengine/Ketsji/KX_PyMath.cpp b/source/gameengine/Ketsji/KX_PyMath.cpp index 76cfb0e572d..051d7ae7dba 100644 --- a/source/gameengine/Ketsji/KX_PyMath.cpp +++ b/source/gameengine/Ketsji/KX_PyMath.cpp @@ -46,6 +46,35 @@ #include "KX_Python.h" #include "KX_PyMath.h" +bool PyObject_IsMT_Matrix(PyObject *pymat, unsigned int rank) +{ + if (!pymat) + return false; + + unsigned int y; + if (PySequence_Check(pymat)) + { + unsigned int rows = PySequence_Size(pymat); + if (rows != rank) + return false; + + bool ismatrix = true; + for (y = 0; y < rank && ismatrix; y++) + { + PyObject *pyrow = PySequence_GetItem(pymat, y); /* new ref */ + if (PySequence_Check(pyrow)) + { + if (((unsigned int)PySequence_Size(pyrow)) != rank) + ismatrix = false; + } else + ismatrix = false; + Py_DECREF(pyrow); + } + return ismatrix; + } + return false; +} + bool PyOrientationTo(PyObject* pyval, MT_Matrix3x3 &rot, const char *error_prefix) { int size= PySequence_Size(pyval); @@ -53,7 +82,7 @@ bool PyOrientationTo(PyObject* pyval, MT_Matrix3x3 &rot, const char *error_prefi if (size == 4) { MT_Quaternion qrot; - if (PyQuatTo(pyval, qrot)) + if (PyVecTo(pyval, qrot)) { rot.setRotation(qrot); return true; @@ -79,27 +108,14 @@ bool PyOrientationTo(PyObject* pyval, MT_Matrix3x3 &rot, const char *error_prefi return false; } -bool PyQuatTo(PyObject* pyval, MT_Quaternion &qrot) -{ - if(!PyVecTo(pyval, qrot)) - return false; - - /* annoying!, Blender/Mathutils have the W axis first! */ - MT_Scalar w= qrot[0]; /* from python, this is actually the W */ - qrot[0]= qrot[1]; - qrot[1]= qrot[2]; - qrot[2]= qrot[3]; - qrot[3]= w; - - return true; -} - PyObject* PyObjectFrom(const MT_Matrix4x4 &mat) { -#ifdef USE_MATHUTILS - float fmat[16]; - mat.getValue(fmat); - return newMatrixObject(fmat, 4, 4, Py_NEW); +#if 0 + return Py_BuildValue("[[ffff][ffff][ffff][ffff]]", + mat[0][0], mat[0][1], mat[0][2], mat[0][3], + mat[1][0], mat[1][1], mat[1][2], mat[1][3], + mat[2][0], mat[2][1], mat[2][2], mat[2][3], + mat[3][0], mat[3][1], mat[3][2], mat[3][3]); #else PyObject *list = PyList_New(4); PyObject *sublist; @@ -120,10 +136,11 @@ PyObject* PyObjectFrom(const MT_Matrix4x4 &mat) PyObject* PyObjectFrom(const MT_Matrix3x3 &mat) { -#ifdef USE_MATHUTILS - float fmat[9]; - mat.getValue3x3(fmat); - return newMatrixObject(fmat, 3, 3, Py_NEW); +#if 0 + return Py_BuildValue("[[fff][fff][fff]]", + mat[0][0], mat[0][1], mat[0][2], + mat[1][0], mat[1][1], mat[1][2], + mat[2][0], mat[2][1], mat[2][2]); #else PyObject *list = PyList_New(3); PyObject *sublist; @@ -141,20 +158,11 @@ PyObject* PyObjectFrom(const MT_Matrix3x3 &mat) #endif } -#ifdef USE_MATHUTILS -PyObject* PyObjectFrom(const MT_Quaternion &qrot) -{ - /* NOTE, were re-ordering here for Mathutils compat */ - float fvec[4]= {qrot[3], qrot[0], qrot[1], qrot[2]}; - return newQuaternionObject(fvec, Py_WRAP); -} -#endif - PyObject* PyObjectFrom(const MT_Tuple4 &vec) { -#ifdef USE_MATHUTILS - float fvec[4]= {vec[0], vec[1], vec[2], vec[3]}; - return newVectorObject(fvec, 4, Py_WRAP); +#if 0 + return Py_BuildValue("[ffff]", + vec[0], vec[1], vec[2], vec[3]); #else PyObject *list = PyList_New(4); PyList_SET_ITEM(list, 0, PyFloat_FromDouble(vec[0])); @@ -167,9 +175,9 @@ PyObject* PyObjectFrom(const MT_Tuple4 &vec) PyObject* PyObjectFrom(const MT_Tuple3 &vec) { -#ifdef USE_MATHUTILS - float fvec[3]= {vec[0], vec[1], vec[2]}; - return newVectorObject(fvec, 3, Py_WRAP); +#if 0 + return Py_BuildValue("[fff]", + vec[0], vec[1], vec[2]); #else PyObject *list = PyList_New(3); PyList_SET_ITEM(list, 0, PyFloat_FromDouble(vec[0])); @@ -181,9 +189,9 @@ PyObject* PyObjectFrom(const MT_Tuple3 &vec) PyObject* PyObjectFrom(const MT_Tuple2 &vec) { -#ifdef USE_MATHUTILS - float fvec[2]= {vec[0], vec[1]}; - return newVectorObject(fvec, 2, Py_WRAP); +#if 0 + return Py_BuildValue("[ff]", + vec[0], vec[1]); #else PyObject *list = PyList_New(2); PyList_SET_ITEM(list, 0, PyFloat_FromDouble(vec[0])); diff --git a/source/gameengine/Ketsji/KX_PyMath.h b/source/gameengine/Ketsji/KX_PyMath.h index 9ee11c9e745..a7ce4bc6930 100644 --- a/source/gameengine/Ketsji/KX_PyMath.h +++ b/source/gameengine/Ketsji/KX_PyMath.h @@ -42,12 +42,6 @@ #include "KX_Python.h" #include "PyObjectPlus.h" -#ifdef USE_MATHUTILS -extern "C" { -#include "../../blender/python/generic/Mathutils.h" /* so we can have mathutils callbacks */ -} -#endif - inline unsigned int Size(const MT_Matrix4x4&) { return 4; } inline unsigned int Size(const MT_Matrix3x3&) { return 3; } inline unsigned int Size(const MT_Tuple2&) { return 2; } @@ -104,38 +98,7 @@ bool PyMatTo(PyObject* pymat, T& mat) template<class T> bool PyVecTo(PyObject* pyval, T& vec) { -#ifdef USE_MATHUTILS - /* no need for BaseMath_ReadCallback() here, reading the sequences will do this */ - - if(VectorObject_Check(pyval)) { - VectorObject *pyvec= (VectorObject *)pyval; - if (pyvec->size != Size(vec)) { - PyErr_Format(PyExc_AttributeError, "error setting vector, %d args, should be %d", pyvec->size, Size(vec)); - return false; - } - vec.getValue((float *) pyvec->vec); - return true; - } - else if(QuaternionObject_Check(pyval)) { - QuaternionObject *pyquat= (QuaternionObject *)pyval; - if (4 != Size(vec)) { - PyErr_Format(PyExc_AttributeError, "error setting vector, %d args, should be %d", 4, Size(vec)); - return false; - } - /* xyzw -> wxyz reordering is done by PyQuatTo */ - vec.getValue((float *) pyquat->quat); - return true; - } - else if(EulerObject_Check(pyval)) { - EulerObject *pyeul= (EulerObject *)pyval; - if (3 != Size(vec)) { - PyErr_Format(PyExc_AttributeError, "error setting vector, %d args, should be %d", 3, Size(vec)); - return false; - } - vec.getValue((float *) pyeul->eul); - return true; - } else -#endif + if(PyTuple_Check(pyval)) { unsigned int numitems = PyTuple_GET_SIZE(pyval); @@ -154,7 +117,7 @@ bool PyVecTo(PyObject* pyval, T& vec) return true; } - else if (PyObject_TypeCheck(pyval, &PyObjectPlus::Type)) + else if (BGE_PROXY_CHECK_TYPE(pyval)) { /* note, include this check because PySequence_Check does too much introspection * on the PyObject (like getting its __class__, on a BGE type this means searching up * the parent list each time only to discover its not a sequence. @@ -196,9 +159,6 @@ bool PyVecTo(PyObject* pyval, T& vec) return false; } - -bool PyQuatTo(PyObject* pyval, MT_Quaternion &qrot); - bool PyOrientationTo(PyObject* pyval, MT_Matrix3x3 &mat, const char *error_prefix); /** @@ -221,16 +181,15 @@ PyObject* PyObjectFrom(const MT_Tuple2 &vec); */ PyObject* PyObjectFrom(const MT_Tuple3 &vec); -#ifdef USE_MATHUTILS /** - * Converts an MT_Quaternion to a python object. + * Converts an MT_Tuple4 to a python object. */ -PyObject* PyObjectFrom(const MT_Quaternion &qrot); -#endif +PyObject* PyObjectFrom(const MT_Tuple4 &pos); /** - * Converts an MT_Tuple4 to a python object. + * True if the given PyObject can be converted to an MT_Matrix + * @param rank = 3 (for MT_Matrix3x3) or 4 (for MT_Matrix4x4) */ -PyObject* PyObjectFrom(const MT_Tuple4 &pos); +bool PyObject_IsMT_Matrix(PyObject *pymat, unsigned int rank); #endif diff --git a/source/gameengine/Ketsji/KX_PythonInit.cpp b/source/gameengine/Ketsji/KX_PythonInit.cpp index eead7a51885..736460d33db 100644 --- a/source/gameengine/Ketsji/KX_PythonInit.cpp +++ b/source/gameengine/Ketsji/KX_PythonInit.cpp @@ -130,10 +130,10 @@ void KX_RasterizerDrawDebugLine(const MT_Vector3& from,const MT_Vector3& to,cons } /* Macro for building the keyboard translation */ -//#define KX_MACRO_addToDict(dict, name) PyDict_SetItemString(dict, #name, PyLong_FromSsize_t(SCA_IInputDevice::KX_##name)) -#define KX_MACRO_addToDict(dict, name) PyDict_SetItemString(dict, #name, item=PyLong_FromSsize_t(name)); Py_DECREF(item) +//#define KX_MACRO_addToDict(dict, name) PyDict_SetItemString(dict, #name, PyInt_FromLong(SCA_IInputDevice::KX_##name)) +#define KX_MACRO_addToDict(dict, name) PyDict_SetItemString(dict, #name, item=PyInt_FromLong(name)); Py_DECREF(item) /* For the defines for types from logic bricks, we do stuff explicitly... */ -#define KX_MACRO_addTypesToDict(dict, name, name2) PyDict_SetItemString(dict, #name, item=PyLong_FromSsize_t(name2)); Py_DECREF(item) +#define KX_MACRO_addTypesToDict(dict, name, name2) PyDict_SetItemString(dict, #name, item=PyInt_FromLong(name2)); Py_DECREF(item) // temporarily python stuff, will be put in another place later ! @@ -181,7 +181,7 @@ static PyObject* gPyExpandPath(PyObject*, PyObject* args) BLI_strncpy(expanded, filename, FILE_MAXDIR + FILE_MAXFILE); BLI_convertstringcode(expanded, gp_GamePythonPath); - return PyUnicode_FromString(expanded); + return PyString_FromString(expanded); } static char gPySendMessage_doc[] = @@ -306,7 +306,7 @@ static PyObject* gPySetMaxLogicFrame(PyObject*, PyObject* args) static PyObject* gPyGetMaxLogicFrame(PyObject*) { - return PyLong_FromSsize_t(KX_KetsjiEngine::GetMaxLogicFrame()); + return PyInt_FromLong(KX_KetsjiEngine::GetMaxLogicFrame()); } static PyObject* gPySetMaxPhysicsFrame(PyObject*, PyObject* args) @@ -321,7 +321,7 @@ static PyObject* gPySetMaxPhysicsFrame(PyObject*, PyObject* args) static PyObject* gPyGetMaxPhysicsFrame(PyObject*) { - return PyLong_FromSsize_t(KX_KetsjiEngine::GetMaxPhysicsFrame()); + return PyInt_FromLong(KX_KetsjiEngine::GetMaxPhysicsFrame()); } static PyObject* gPySetPhysicsTicRate(PyObject*, PyObject* args) @@ -386,7 +386,7 @@ static PyObject* gPyGetBlendFileList(PyObject*, PyObject* args) while ((dirp = readdir(dp)) != NULL) { if (BLI_testextensie(dirp->d_name, ".blend")) { - value = PyUnicode_FromString(dirp->d_name); + value = PyString_FromString(dirp->d_name); PyList_Append(list, value); Py_DECREF(value); } @@ -500,7 +500,7 @@ static PyObject *pyPrintExt(PyObject *,PyObject *,PyObject *) static PyObject *gEvalExpression(PyObject*, PyObject* value) { - char* txt= _PyUnicode_AsString(value); + char* txt= PyString_AsString(value); if (txt==NULL) { PyErr_SetString(PyExc_TypeError, "Expression.calc(text): expects a single string argument"); @@ -558,14 +558,14 @@ static struct PyMethodDef game_methods[] = { static PyObject* gPyGetWindowHeight(PyObject*, PyObject* args) { - return PyLong_FromSsize_t((gp_Canvas ? gp_Canvas->GetHeight() : 0)); + return PyInt_FromLong((gp_Canvas ? gp_Canvas->GetHeight() : 0)); } static PyObject* gPyGetWindowWidth(PyObject*, PyObject* args) { - return PyLong_FromSsize_t((gp_Canvas ? gp_Canvas->GetWidth() : 0)); + return PyInt_FromLong((gp_Canvas ? gp_Canvas->GetWidth() : 0)); } @@ -893,7 +893,7 @@ static PyObject* gPyGetGLSLMaterialSetting(PyObject*, } enabled = ((G.fileflags & flag) != 0); - return PyLong_FromSsize_t(enabled); + return PyInt_FromLong(enabled); } #define KX_TEXFACE_MATERIAL 0 @@ -937,7 +937,7 @@ static PyObject* gPyGetMaterialType(PyObject*) else flag = KX_TEXFACE_MATERIAL; - return PyLong_FromSsize_t(flag); + return PyInt_FromLong(flag); } static PyObject* gPyDrawLine(PyObject*, PyObject* args) @@ -1075,7 +1075,7 @@ PyObject* initGameLogic(KX_KetsjiEngine *engine, KX_Scene* scene) // quick hack PyDict_SetItemString(d, "globalDict", item=PyDict_New()); Py_DECREF(item); - ErrorObject = PyUnicode_FromString("GameLogic.error"); + ErrorObject = PyString_FromString("GameLogic.error"); PyDict_SetItemString(d, "error", ErrorObject); Py_DECREF(ErrorObject); @@ -1362,7 +1362,7 @@ PyObject *KXpy_import(PyObject *self, PyObject *args) /* check for builtin modules */ m = PyImport_AddModule("sys"); l = PyObject_GetAttrString(m, "builtin_module_names"); - n = PyUnicode_FromString(name); + n = PyString_FromString(name); if (PySequence_Contains(l, n)) { return PyImport_ImportModuleEx(name, globals, locals, fromlist); @@ -1538,7 +1538,7 @@ static void initPySysObjects__append(PyObject *sys_path, char *filename) BLI_split_dirfile_basic(filename, expanded, NULL); /* get the dir part of filename only */ BLI_convertstringcode(expanded, gp_GamePythonPath); /* filename from lib->filename is (always?) absolute, so this may not be needed but it wont hurt */ BLI_cleanup_file(gp_GamePythonPath, expanded); /* Dont use BLI_cleanup_dir because it adds a slash - BREAKS WIN32 ONLY */ - item= PyUnicode_FromString(expanded); + item= PyString_FromString(expanded); // printf("SysPath - '%s', '%s', '%s'\n", expanded, filename, gp_GamePythonPath); @@ -1735,7 +1735,7 @@ PyObject* initRasterizer(RAS_IRasterizer* rasty,RAS_ICanvas* canvas) // Add some symbolic constants to the module d = PyModule_GetDict(m); - ErrorObject = PyUnicode_FromString("Rasterizer.error"); + ErrorObject = PyString_FromString("Rasterizer.error"); PyDict_SetItemString(d, "error", ErrorObject); Py_DECREF(ErrorObject); @@ -1813,10 +1813,10 @@ static PyObject* gPyEventToCharacter(PyObject*, PyObject* args) if(IsPrintable(event)) { char ch[2] = {'\0', '\0'}; ch[0] = ToCharacter(event, (bool)shift); - return PyUnicode_FromString(ch); + return PyString_FromString(ch); } else { - return PyUnicode_FromString(""); + return PyString_FromString(""); } } @@ -2044,7 +2044,7 @@ int saveGamePythonConfig( char **marshal_buffer) char *marshal_cstring; #if PY_VERSION_HEX < 0x03000000 - marshal_cstring = _PyUnicode_AsString(pyGlobalDictMarshal); + marshal_cstring = PyString_AsString(pyGlobalDictMarshal); marshal_length= PyString_Size(pyGlobalDictMarshal); #else // py3 uses byte arrays marshal_cstring = PyBytes_AsString(pyGlobalDictMarshal); diff --git a/source/gameengine/Ketsji/KX_PythonInitTypes.cpp b/source/gameengine/Ketsji/KX_PythonInitTypes.cpp index 8ff0bfd5379..83c4dcbb34c 100644 --- a/source/gameengine/Ketsji/KX_PythonInitTypes.cpp +++ b/source/gameengine/Ketsji/KX_PythonInitTypes.cpp @@ -87,54 +87,69 @@ #include "SCA_RandomActuator.h" #include "SCA_IController.h" -static void PyType_Ready_ADD(PyObject *dict, PyTypeObject *tp, PyAttributeDef *attributes, int init_getset) + +void initPyObjectPlusType(PyTypeObject **parents) { - PyAttributeDef *attr; + int i; - if(init_getset) { - /* we need to do this for all types before calling PyType_Ready - * since they will call the parents PyType_Ready and those might not have initialized vars yet */ + for (i=0; parents[i]; i++) { + if(PyType_Ready(parents[i]) < 0) { + /* This is very very unlikely */ + printf("Error, pytype could not initialize, Blender may crash \"%s\"\n", parents[i]->tp_name); + return; + } - //if(tp->tp_base==NULL) - // printf("Debug: No Parents - '%s'\n" , tp->tp_name); +#if 0 + PyObject_Print(reinterpret_cast<PyObject *>parents[i], stderr, 0); + fprintf(stderr, "\n"); + PyObject_Print(parents[i]->tp_dict, stderr, 0); + fprintf(stderr, "\n\n"); +#endif - if(tp->tp_getset==NULL && attributes->m_name) { - PyGetSetDef *attr_getset; - int attr_tot= 0; + } - for(attr= attributes; attr->m_name; attr++, attr_tot++) {}; + PyObject *dict= NULL; - tp->tp_getset = attr_getset = reinterpret_cast<PyGetSetDef *>(PyMem_Malloc((attr_tot+1) * sizeof(PyGetSetDef))); // XXX - Todo, free + while(i) { + i--; + if (dict) { + PyDict_Update(parents[i]->tp_dict, dict); + } + dict= parents[i]->tp_dict; - for(attr= attributes; attr->m_name; attr++, attr_getset++) { - attr_getset->name= (char *)attr->m_name; - attr_getset->doc= NULL; +#if 1 + PyObject_Print(reinterpret_cast<PyObject *>(parents[i]), stderr, 0); + fprintf(stderr, "\n"); + PyObject_Print(parents[i]->tp_dict, stderr, 0); + fprintf(stderr, "\n\n"); +#endif - attr_getset->get= reinterpret_cast<getter>(PyObjectPlus::py_get_attrdef); + } +} - if(attr->m_access==KX_PYATTRIBUTE_RO) - attr_getset->set= NULL; - else - attr_getset->set= reinterpret_cast<setter>(PyObjectPlus::py_set_attrdef); - attr_getset->closure= reinterpret_cast<void *>(attr); - } - memset(attr_getset, 0, sizeof(PyGetSetDef)); - } - } else { - - PyObject *item; - PyType_Ready(tp); - PyDict_SetItemString(dict, tp->tp_name, reinterpret_cast<PyObject *>(tp)); +static void PyType_Ready_ADD(PyObject *dict, PyTypeObject *tp, PyAttributeDef *attributes) +{ + PyAttributeDef *attr; + PyObject *item; + + PyType_Ready(tp); + PyDict_SetItemString(dict, tp->tp_name, reinterpret_cast<PyObject *>(tp)); + + /* store attr defs in the tp_dict for to avoid string lookups */ + for(attr= attributes; attr->m_name; attr++) { + item= PyCObject_FromVoidPtr(attr, NULL); + PyDict_SetItemString(tp->tp_dict, attr->m_name, item); + Py_DECREF(item); } } -#define PyType_Ready_Attr(d, n, i) PyType_Ready_ADD(d, &n::Type, n::Attributes, i) +#define PyType_Ready_Attr(d, n) PyType_Ready_ADD(d, &n::Type, n::Attributes) void initPyTypes(void) { @@ -150,82 +165,72 @@ void initPyTypes(void) PyDict_SetItemString(PySys_GetObject((char *)"modules"), (char *)"GameTypes", mod); Py_DECREF(mod); + PyType_Ready_Attr(dict, BL_ActionActuator); + PyType_Ready_Attr(dict, BL_Shader); + PyType_Ready_Attr(dict, BL_ShapeActionActuator); + PyType_Ready_Attr(dict, CListValue); + PyType_Ready_Attr(dict, CValue); + PyType_Ready_Attr(dict, KX_BlenderMaterial); + PyType_Ready_Attr(dict, KX_CDActuator); + PyType_Ready_Attr(dict, KX_Camera); + PyType_Ready_Attr(dict, KX_CameraActuator); + PyType_Ready_Attr(dict, KX_ConstraintActuator); + PyType_Ready_Attr(dict, KX_ConstraintWrapper); + PyType_Ready_Attr(dict, KX_GameActuator); + PyType_Ready_Attr(dict, KX_GameObject); + PyType_Ready_Attr(dict, KX_IpoActuator); + PyType_Ready_Attr(dict, KX_LightObject); + PyType_Ready_Attr(dict, KX_MeshProxy); + PyType_Ready_Attr(dict, KX_MouseFocusSensor); + PyType_Ready_Attr(dict, KX_NearSensor); + PyType_Ready_Attr(dict, KX_NetworkMessageActuator); + PyType_Ready_Attr(dict, KX_NetworkMessageSensor); + PyType_Ready_Attr(dict, KX_ObjectActuator); + PyType_Ready_Attr(dict, KX_ParentActuator); + PyType_Ready_Attr(dict, KX_PhysicsObjectWrapper); + PyType_Ready_Attr(dict, KX_PolyProxy); + PyType_Ready_Attr(dict, KX_PolygonMaterial); + PyType_Ready_Attr(dict, KX_RadarSensor); + PyType_Ready_Attr(dict, KX_RaySensor); + PyType_Ready_Attr(dict, KX_SCA_AddObjectActuator); + PyType_Ready_Attr(dict, KX_SCA_DynamicActuator); + PyType_Ready_Attr(dict, KX_SCA_EndObjectActuator); + PyType_Ready_Attr(dict, KX_SCA_ReplaceMeshActuator); + PyType_Ready_Attr(dict, KX_Scene); + PyType_Ready_Attr(dict, KX_SceneActuator); + PyType_Ready_Attr(dict, KX_SoundActuator); + PyType_Ready_Attr(dict, KX_StateActuator); + PyType_Ready_Attr(dict, KX_TouchSensor); + PyType_Ready_Attr(dict, KX_TrackToActuator); + PyType_Ready_Attr(dict, KX_VehicleWrapper); + PyType_Ready_Attr(dict, KX_VertexProxy); + PyType_Ready_Attr(dict, KX_VisibilityActuator); + PyType_Ready_Attr(dict, PyObjectPlus); + PyType_Ready_Attr(dict, SCA_2DFilterActuator); + PyType_Ready_Attr(dict, SCA_ANDController); + PyType_Ready_Attr(dict, SCA_ActuatorSensor); + PyType_Ready_Attr(dict, SCA_AlwaysSensor); + PyType_Ready_Attr(dict, SCA_DelaySensor); + PyType_Ready_Attr(dict, SCA_ILogicBrick); + PyType_Ready_Attr(dict, SCA_IObject); + PyType_Ready_Attr(dict, SCA_ISensor); + PyType_Ready_Attr(dict, SCA_JoystickSensor); + PyType_Ready_Attr(dict, SCA_KeyboardSensor); + PyType_Ready_Attr(dict, SCA_MouseSensor); + PyType_Ready_Attr(dict, SCA_NANDController); + PyType_Ready_Attr(dict, SCA_NORController); + PyType_Ready_Attr(dict, SCA_ORController); + PyType_Ready_Attr(dict, SCA_PropertyActuator); + PyType_Ready_Attr(dict, SCA_PropertySensor); + PyType_Ready_Attr(dict, SCA_PythonController); + PyType_Ready_Attr(dict, SCA_RandomActuator); + PyType_Ready_Attr(dict, SCA_RandomSensor); + PyType_Ready_Attr(dict, SCA_XNORController); + PyType_Ready_Attr(dict, SCA_XORController); + PyType_Ready_Attr(dict, SCA_IController); - for(int init_getset= 1; init_getset > -1; init_getset--) { /* run twice, once to init the getsets another to run PyType_Ready */ - PyType_Ready_Attr(dict, BL_ActionActuator, init_getset); - PyType_Ready_Attr(dict, BL_Shader, init_getset); - PyType_Ready_Attr(dict, BL_ShapeActionActuator, init_getset); - PyType_Ready_Attr(dict, CListValue, init_getset); - PyType_Ready_Attr(dict, CValue, init_getset); - PyType_Ready_Attr(dict, KX_BlenderMaterial, init_getset); - PyType_Ready_Attr(dict, KX_CDActuator, init_getset); - PyType_Ready_Attr(dict, KX_Camera, init_getset); - PyType_Ready_Attr(dict, KX_CameraActuator, init_getset); - PyType_Ready_Attr(dict, KX_ConstraintActuator, init_getset); - PyType_Ready_Attr(dict, KX_ConstraintWrapper, init_getset); - PyType_Ready_Attr(dict, KX_GameActuator, init_getset); - PyType_Ready_Attr(dict, KX_GameObject, init_getset); - PyType_Ready_Attr(dict, KX_IpoActuator, init_getset); - PyType_Ready_Attr(dict, KX_LightObject, init_getset); - PyType_Ready_Attr(dict, KX_MeshProxy, init_getset); - PyType_Ready_Attr(dict, KX_MouseFocusSensor, init_getset); - PyType_Ready_Attr(dict, KX_NearSensor, init_getset); - PyType_Ready_Attr(dict, KX_NetworkMessageActuator, init_getset); - PyType_Ready_Attr(dict, KX_NetworkMessageSensor, init_getset); - PyType_Ready_Attr(dict, KX_ObjectActuator, init_getset); - PyType_Ready_Attr(dict, KX_ParentActuator, init_getset); - PyType_Ready_Attr(dict, KX_PhysicsObjectWrapper, init_getset); - PyType_Ready_Attr(dict, KX_PolyProxy, init_getset); - PyType_Ready_Attr(dict, KX_PolygonMaterial, init_getset); - PyType_Ready_Attr(dict, KX_RadarSensor, init_getset); - PyType_Ready_Attr(dict, KX_RaySensor, init_getset); - PyType_Ready_Attr(dict, KX_SCA_AddObjectActuator, init_getset); - PyType_Ready_Attr(dict, KX_SCA_DynamicActuator, init_getset); - PyType_Ready_Attr(dict, KX_SCA_EndObjectActuator, init_getset); - PyType_Ready_Attr(dict, KX_SCA_ReplaceMeshActuator, init_getset); - PyType_Ready_Attr(dict, KX_Scene, init_getset); - PyType_Ready_Attr(dict, KX_SceneActuator, init_getset); - PyType_Ready_Attr(dict, KX_SoundActuator, init_getset); - PyType_Ready_Attr(dict, KX_StateActuator, init_getset); - PyType_Ready_Attr(dict, KX_TouchSensor, init_getset); - PyType_Ready_Attr(dict, KX_TrackToActuator, init_getset); - PyType_Ready_Attr(dict, KX_VehicleWrapper, init_getset); - PyType_Ready_Attr(dict, KX_VertexProxy, init_getset); - PyType_Ready_Attr(dict, KX_VisibilityActuator, init_getset); - PyType_Ready_Attr(dict, PyObjectPlus, init_getset); - PyType_Ready_Attr(dict, SCA_2DFilterActuator, init_getset); - PyType_Ready_Attr(dict, SCA_ANDController, init_getset); - PyType_Ready_Attr(dict, SCA_ActuatorSensor, init_getset); - PyType_Ready_Attr(dict, SCA_AlwaysSensor, init_getset); - PyType_Ready_Attr(dict, SCA_DelaySensor, init_getset); - PyType_Ready_Attr(dict, SCA_ILogicBrick, init_getset); - PyType_Ready_Attr(dict, SCA_IObject, init_getset); - PyType_Ready_Attr(dict, SCA_ISensor, init_getset); - PyType_Ready_Attr(dict, SCA_JoystickSensor, init_getset); - PyType_Ready_Attr(dict, SCA_KeyboardSensor, init_getset); - PyType_Ready_Attr(dict, SCA_MouseSensor, init_getset); - PyType_Ready_Attr(dict, SCA_NANDController, init_getset); - PyType_Ready_Attr(dict, SCA_NORController, init_getset); - PyType_Ready_Attr(dict, SCA_ORController, init_getset); - PyType_Ready_Attr(dict, SCA_PropertyActuator, init_getset); - PyType_Ready_Attr(dict, SCA_PropertySensor, init_getset); - PyType_Ready_Attr(dict, SCA_PythonController, init_getset); - PyType_Ready_Attr(dict, SCA_RandomActuator, init_getset); - PyType_Ready_Attr(dict, SCA_RandomSensor, init_getset); - PyType_Ready_Attr(dict, SCA_XNORController, init_getset); - PyType_Ready_Attr(dict, SCA_XORController, init_getset); - PyType_Ready_Attr(dict, SCA_IController, init_getset); - } - - /* Normal python type */ PyType_Ready(&KX_PythonSeq_Type); - -#ifdef USE_MATHUTILS - /* Init mathutils callbacks */ - KX_GameObject_Mathutils_Callback_Init(); - KX_ObjectActuator_Mathutils_Callback_Init(); -#endif } -#endif +#endif
\ No newline at end of file diff --git a/source/gameengine/Ketsji/KX_PythonSeq.cpp b/source/gameengine/Ketsji/KX_PythonSeq.cpp index 5b4d77156db..524d957a80c 100644 --- a/source/gameengine/Ketsji/KX_PythonSeq.cpp +++ b/source/gameengine/Ketsji/KX_PythonSeq.cpp @@ -221,11 +221,11 @@ static PyObject * KX_PythonSeq_subscript(PyObject * self, PyObject *key) return NULL; } - if (PyLong_Check(key)) { - return KX_PythonSeq_getIndex(self, PyLong_AsSsize_t( key )); + if (PyInt_Check(key)) { + return KX_PythonSeq_getIndex(self, PyInt_AS_LONG( key )); } - else if ( PyUnicode_Check(key) ) { - char *name = _PyUnicode_AsString(key); + else if ( PyString_Check(key) ) { + char *name = PyString_AsString(key); PyObjectPlus *ret = KX_PythonSeq_subscript__internal(self, name); if(ret) { @@ -250,12 +250,12 @@ static int KX_PythonSeq_contains(PyObject *self, PyObject *key) PyErr_SetString(PyExc_SystemError, "key in seq, KX_PythonSeq: "BGE_PROXY_ERROR_MSG); return -1; } - if(!PyUnicode_Check(key)) { + if(!PyString_Check(key)) { PyErr_SetString(PyExc_SystemError, "key in seq, KX_PythonSeq: key must be a string"); return -1; } - if(KX_PythonSeq_subscript__internal(self, _PyUnicode_AsString(key))) + if(KX_PythonSeq_subscript__internal(self, PyString_AsString(key))) return 1; return 0; diff --git a/source/gameengine/Ketsji/KX_RadarSensor.cpp b/source/gameengine/Ketsji/KX_RadarSensor.cpp index e39d3756b71..064dc9126ac 100644 --- a/source/gameengine/Ketsji/KX_RadarSensor.cpp +++ b/source/gameengine/Ketsji/KX_RadarSensor.cpp @@ -49,7 +49,8 @@ KX_RadarSensor::KX_RadarSensor(SCA_EventManager* eventmgr, double resetmargin, bool bFindMaterial, const STR_String& touchedpropname, - class KX_Scene* kxscene) + class KX_Scene* kxscene, + PyTypeObject* T) : KX_NearSensor( eventmgr, @@ -60,8 +61,8 @@ KX_RadarSensor::KX_RadarSensor(SCA_EventManager* eventmgr, bFindMaterial, touchedpropname, kxscene, - physCtrl), - + physCtrl, + T), m_coneradius(coneradius), m_coneheight(coneheight), m_axis(axis) @@ -244,15 +245,21 @@ PyTypeObject KX_RadarSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_RadarSensor::Parents[] = { + &KX_RadarSensor::Type, &KX_NearSensor::Type, - 0,0,0,0,0,0, - py_base_new + &KX_TouchSensor::Type, + &SCA_ISensor::Type, + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_RadarSensor::Methods[] = { @@ -276,3 +283,16 @@ PyAttributeDef KX_RadarSensor::Attributes[] = { {NULL} //Sentinel }; +PyObject* KX_RadarSensor::py_getattro(PyObject *attr) +{ + py_getattro_up(KX_NearSensor); +} + +PyObject* KX_RadarSensor::py_getattro_dict() { + py_getattro_dict_up(KX_NearSensor); +} + +int KX_RadarSensor::py_setattro(PyObject *attr, PyObject* value) +{ + py_setattro_up(KX_NearSensor); +} diff --git a/source/gameengine/Ketsji/KX_RadarSensor.h b/source/gameengine/Ketsji/KX_RadarSensor.h index 344be0e399f..2e5a0e68bed 100644 --- a/source/gameengine/Ketsji/KX_RadarSensor.h +++ b/source/gameengine/Ketsji/KX_RadarSensor.h @@ -70,7 +70,8 @@ public: double resetmargin, bool bFindMaterial, const STR_String& touchedpropname, - class KX_Scene* kxscene); + class KX_Scene* kxscene, + PyTypeObject* T = &Type); KX_RadarSensor(); virtual ~KX_RadarSensor(); virtual void SynchronizeTransform(); @@ -88,7 +89,9 @@ public: KX_RADAR_AXIS_NEG_Z }; - /* python */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); virtual sensortype GetSensorType() { return ST_RADAR; } //Deprecated -----> diff --git a/source/gameengine/Ketsji/KX_RaySensor.cpp b/source/gameengine/Ketsji/KX_RaySensor.cpp index 3f27496df71..78a61e9d95e 100644 --- a/source/gameengine/Ketsji/KX_RaySensor.cpp +++ b/source/gameengine/Ketsji/KX_RaySensor.cpp @@ -55,8 +55,9 @@ KX_RaySensor::KX_RaySensor(class SCA_EventManager* eventmgr, bool bXRay, double distance, int axis, - KX_Scene* ketsjiScene) - : SCA_ISensor(gameobj,eventmgr), + KX_Scene* ketsjiScene, + PyTypeObject* T) + : SCA_ISensor(gameobj,eventmgr, T), m_propertyname(propname), m_bFindMaterial(bFindMaterial), m_bXRay(bXRay), @@ -335,16 +336,20 @@ PyTypeObject KX_RaySensor::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &SCA_ISensor::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods + +}; +PyParentObject KX_RaySensor::Parents[] = { + &KX_RaySensor::Type, + &SCA_ISensor::Type, + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_RaySensor::Methods[] = { @@ -442,4 +447,18 @@ PyObject* KX_RaySensor::PyGetHitNormal() return retVal; } + + +PyObject* KX_RaySensor::py_getattro(PyObject *attr) { + py_getattro_up(SCA_ISensor); +} + +PyObject* KX_RaySensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + +int KX_RaySensor::py_setattro(PyObject *attr, PyObject *value) { + py_setattro_up(SCA_ISensor); +} + // <----- Deprecated diff --git a/source/gameengine/Ketsji/KX_RaySensor.h b/source/gameengine/Ketsji/KX_RaySensor.h index 530c8ce54e5..9efb046742f 100644 --- a/source/gameengine/Ketsji/KX_RaySensor.h +++ b/source/gameengine/Ketsji/KX_RaySensor.h @@ -62,7 +62,8 @@ public: bool bXRay, double distance, int axis, - class KX_Scene* ketsjiScene); + class KX_Scene* ketsjiScene, + PyTypeObject* T = &Type); virtual ~KX_RaySensor(); virtual CValue* GetReplica(); @@ -83,6 +84,11 @@ public: KX_RAY_AXIS_NEG_Y, KX_RAY_AXIS_NEG_Z }; + + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); // Deprecated -----> KX_PYMETHOD_DOC_NOARGS(KX_RaySensor,GetHitObject); diff --git a/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.cpp b/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.cpp index 239c4a0be67..75435b97797 100644 --- a/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.cpp +++ b/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.cpp @@ -55,9 +55,10 @@ KX_SCA_AddObjectActuator::KX_SCA_AddObjectActuator(SCA_IObject *gameobj, const float *linvel, bool linv_local, const float *angvel, - bool angv_local) + bool angv_local, + PyTypeObject* T) : - SCA_IActuator(gameobj), + SCA_IActuator(gameobj, T), m_OriginalObject(original), m_scene(scene), @@ -186,17 +187,20 @@ PyTypeObject KX_SCA_AddObjectActuator::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &SCA_IActuator::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods }; +PyParentObject KX_SCA_AddObjectActuator::Parents[] = { + &KX_SCA_AddObjectActuator::Type, + &SCA_IActuator::Type, + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL +}; PyMethodDef KX_SCA_AddObjectActuator::Methods[] = { // ---> deprecated {"setTime", (PyCFunction) KX_SCA_AddObjectActuator::sPySetTime, METH_O, (PY_METHODCHAR)SetTime_doc}, @@ -259,6 +263,21 @@ PyObject* KX_SCA_AddObjectActuator::pyattr_get_objectLastCreated(void *self, con return actuator->m_lastCreatedObject->GetProxy(); } + +PyObject* KX_SCA_AddObjectActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_SCA_AddObjectActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_SCA_AddObjectActuator::py_setattro(PyObject *attr, PyObject* value) +{ + py_setattro_up(SCA_IActuator); +} + /* 1. setObject */ const char KX_SCA_AddObjectActuator::SetObject_doc[] = "setObject(object)\n" @@ -297,7 +316,7 @@ const char KX_SCA_AddObjectActuator::SetTime_doc[] = PyObject* KX_SCA_AddObjectActuator::PySetTime(PyObject* value) { ShowDeprecationWarning("setTime()", "the time property"); - int deltatime = PyLong_AsSsize_t(value); + int deltatime = PyInt_AsLong(value); if (deltatime==-1 && PyErr_Occurred()) { PyErr_SetString(PyExc_TypeError, "expected an int"); return NULL; @@ -320,7 +339,7 @@ const char KX_SCA_AddObjectActuator::GetTime_doc[] = PyObject* KX_SCA_AddObjectActuator::PyGetTime() { ShowDeprecationWarning("getTime()", "the time property"); - return PyLong_FromSsize_t(m_timeProp); + return PyInt_FromLong(m_timeProp); } @@ -342,7 +361,7 @@ PyObject* KX_SCA_AddObjectActuator::PyGetObject(PyObject* args) Py_RETURN_NONE; if (ret_name_only) - return PyUnicode_FromString(m_OriginalObject->GetName().ReadPtr()); + return PyString_FromString(m_OriginalObject->GetName().ReadPtr()); else return m_OriginalObject->GetProxy(); } diff --git a/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.h b/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.h index 3151e7a89ca..6746b7d1bc6 100644 --- a/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.h +++ b/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.h @@ -88,7 +88,8 @@ public: const float *linvel, bool linv_local, const float *angvel, - bool angv_local + bool angv_local, + PyTypeObject* T=&Type ); ~KX_SCA_AddObjectActuator(void); @@ -109,6 +110,10 @@ public: virtual bool Update(); + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); + SCA_IObject* GetLastCreatedObject( ) const ; diff --git a/source/gameengine/Ketsji/KX_SCA_DynamicActuator.cpp b/source/gameengine/Ketsji/KX_SCA_DynamicActuator.cpp index 423fd0db7f2..a50764a54e6 100644 --- a/source/gameengine/Ketsji/KX_SCA_DynamicActuator.cpp +++ b/source/gameengine/Ketsji/KX_SCA_DynamicActuator.cpp @@ -47,7 +47,9 @@ /* Integration hooks ------------------------------------------------------- */ -PyTypeObject KX_SCA_DynamicActuator::Type = { + PyTypeObject + +KX_SCA_DynamicActuator::Type = { #if (PY_VERSION_HEX >= 0x02060000) PyVarObject_HEAD_INIT(NULL, 0) #else @@ -64,17 +66,22 @@ PyTypeObject KX_SCA_DynamicActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_SCA_DynamicActuator::Parents[] = { + &KX_SCA_DynamicActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; + PyMethodDef KX_SCA_DynamicActuator::Methods[] = { // ---> deprecated KX_PYMETHODTABLE(KX_SCA_DynamicActuator, setOperation), @@ -89,6 +96,21 @@ PyAttributeDef KX_SCA_DynamicActuator::Attributes[] = { }; +PyObject* KX_SCA_DynamicActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_SCA_DynamicActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_SCA_DynamicActuator::py_setattro(PyObject *attr, PyObject* value) +{ + py_setattro_up(SCA_IActuator); +} + + /* 1. setOperation */ KX_PYMETHODDEF_DOC(KX_SCA_DynamicActuator, setOperation, "setOperation(operation?)\n" @@ -120,7 +142,7 @@ KX_PYMETHODDEF_DOC(KX_SCA_DynamicActuator, getOperation, ) { ShowDeprecationWarning("getOperation()", "the mode property"); - return PyLong_FromSsize_t((long)m_dyn_operation); + return PyInt_FromLong((long)m_dyn_operation); } @@ -130,9 +152,10 @@ KX_PYMETHODDEF_DOC(KX_SCA_DynamicActuator, getOperation, KX_SCA_DynamicActuator::KX_SCA_DynamicActuator(SCA_IObject *gameobj, short dyn_operation, - float setmass) : + float setmass, + PyTypeObject* T) : - SCA_IActuator(gameobj), + SCA_IActuator(gameobj, T), m_dyn_operation(dyn_operation), m_setmass(setmass) { diff --git a/source/gameengine/Ketsji/KX_SCA_DynamicActuator.h b/source/gameengine/Ketsji/KX_SCA_DynamicActuator.h index 8b598c9ecfa..4add707f8cd 100644 --- a/source/gameengine/Ketsji/KX_SCA_DynamicActuator.h +++ b/source/gameengine/Ketsji/KX_SCA_DynamicActuator.h @@ -50,7 +50,8 @@ class KX_SCA_DynamicActuator : public SCA_IActuator KX_SCA_DynamicActuator( SCA_IObject* gameobj, short dyn_operation, - float setmass + float setmass, + PyTypeObject* T=&Type ); ~KX_SCA_DynamicActuator( @@ -72,6 +73,11 @@ class KX_SCA_DynamicActuator : public SCA_IActuator KX_DYN_SET_MASS, }; + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + /* 1. setOperation */ KX_PYMETHOD_DOC(KX_SCA_DynamicActuator,setOperation); KX_PYMETHOD_DOC(KX_SCA_DynamicActuator,getOperation); diff --git a/source/gameengine/Ketsji/KX_SCA_EndObjectActuator.cpp b/source/gameengine/Ketsji/KX_SCA_EndObjectActuator.cpp index 47c5c3aeeeb..728254e7f48 100644 --- a/source/gameengine/Ketsji/KX_SCA_EndObjectActuator.cpp +++ b/source/gameengine/Ketsji/KX_SCA_EndObjectActuator.cpp @@ -43,8 +43,9 @@ #endif KX_SCA_EndObjectActuator::KX_SCA_EndObjectActuator(SCA_IObject *gameobj, - SCA_IScene* scene): - SCA_IActuator(gameobj), + SCA_IScene* scene, + PyTypeObject* T): + SCA_IActuator(gameobj, T), m_scene(scene) { // intentionally empty @@ -107,17 +108,24 @@ PyTypeObject KX_SCA_EndObjectActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + +PyParentObject KX_SCA_EndObjectActuator::Parents[] = { + &KX_SCA_EndObjectActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; + + PyMethodDef KX_SCA_EndObjectActuator::Methods[] = { {NULL,NULL} //Sentinel }; @@ -126,4 +134,13 @@ PyAttributeDef KX_SCA_EndObjectActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_SCA_EndObjectActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_SCA_EndObjectActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + /* eof */ diff --git a/source/gameengine/Ketsji/KX_SCA_EndObjectActuator.h b/source/gameengine/Ketsji/KX_SCA_EndObjectActuator.h index 782a24b1ef1..70d72f1f8da 100644 --- a/source/gameengine/Ketsji/KX_SCA_EndObjectActuator.h +++ b/source/gameengine/Ketsji/KX_SCA_EndObjectActuator.h @@ -47,7 +47,8 @@ class KX_SCA_EndObjectActuator : public SCA_IActuator public: KX_SCA_EndObjectActuator( SCA_IObject* gameobj, - SCA_IScene* scene + SCA_IScene* scene, + PyTypeObject* T=&Type ); ~KX_SCA_EndObjectActuator(); @@ -62,6 +63,9 @@ class KX_SCA_EndObjectActuator : public SCA_IActuator /* --------------------------------------------------------------------- */ /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); }; /* end of class KX_EditObjectActuator : public SCA_PropertyActuator */ diff --git a/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp b/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp index 2884bb76565..00842d7012a 100644 --- a/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp +++ b/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp @@ -50,7 +50,9 @@ /* Integration hooks ------------------------------------------------------- */ -PyTypeObject KX_SCA_ReplaceMeshActuator::Type = { + PyTypeObject + +KX_SCA_ReplaceMeshActuator::Type = { #if (PY_VERSION_HEX >= 0x02060000) PyVarObject_HEAD_INIT(NULL, 0) #else @@ -67,17 +69,23 @@ PyTypeObject KX_SCA_ReplaceMeshActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_SCA_ReplaceMeshActuator::Parents[] = { + &KX_SCA_ReplaceMeshActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; + + PyMethodDef KX_SCA_ReplaceMeshActuator::Methods[] = { KX_PYMETHODTABLE(KX_SCA_ReplaceMeshActuator, instantReplaceMesh), // Deprecated -----> @@ -91,6 +99,20 @@ PyAttributeDef KX_SCA_ReplaceMeshActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_SCA_ReplaceMeshActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_SCA_ReplaceMeshActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_SCA_ReplaceMeshActuator::py_setattro(PyObject *attr, PyObject* value) +{ + py_setattro_up(SCA_IActuator); +} + PyObject* KX_SCA_ReplaceMeshActuator::pyattr_get_mesh(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef) { KX_SCA_ReplaceMeshActuator* actuator = static_cast<KX_SCA_ReplaceMeshActuator*>(self); @@ -139,7 +161,7 @@ KX_PYMETHODDEF_DOC(KX_SCA_ReplaceMeshActuator, getMesh, if (!m_mesh) Py_RETURN_NONE; - return PyUnicode_FromString(const_cast<char *>(m_mesh->GetName().ReadPtr())); + return PyString_FromString(const_cast<char *>(m_mesh->GetName().ReadPtr())); } @@ -156,9 +178,10 @@ KX_PYMETHODDEF_DOC(KX_SCA_ReplaceMeshActuator, instantReplaceMesh, KX_SCA_ReplaceMeshActuator::KX_SCA_ReplaceMeshActuator(SCA_IObject *gameobj, class RAS_MeshObject *mesh, - SCA_IScene* scene) : + SCA_IScene* scene, + PyTypeObject* T) : - SCA_IActuator(gameobj), + SCA_IActuator(gameobj, T), m_mesh(mesh), m_scene(scene) { diff --git a/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.h b/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.h index 6a68bd88cc5..0e7f7852701 100644 --- a/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.h +++ b/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.h @@ -55,7 +55,9 @@ class KX_SCA_ReplaceMeshActuator : public SCA_IActuator KX_SCA_ReplaceMeshActuator( SCA_IObject* gameobj, RAS_MeshObject *mesh, - SCA_IScene* scene); + SCA_IScene* scene, + PyTypeObject* T=&Type + ); ~KX_SCA_ReplaceMeshActuator( ); @@ -69,7 +71,10 @@ class KX_SCA_ReplaceMeshActuator : public SCA_IActuator void InstantReplaceMesh(); - /* python api */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); + static PyObject* pyattr_get_mesh(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef); static int pyattr_set_mesh(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value); diff --git a/source/gameengine/Ketsji/KX_Scene.cpp b/source/gameengine/Ketsji/KX_Scene.cpp index 51f5276e075..c0d8a7090c4 100644 --- a/source/gameengine/Ketsji/KX_Scene.cpp +++ b/source/gameengine/Ketsji/KX_Scene.cpp @@ -138,7 +138,7 @@ KX_Scene::KX_Scene(class SCA_IInputDevice* keyboarddevice, class SND_IAudioDevice* adi, const STR_String& sceneName, Scene *scene): - PyObjectPlus(), + PyObjectPlus(&KX_Scene::Type), m_keyboardmgr(NULL), m_mousemgr(NULL), m_sceneConverter(NULL), @@ -1629,15 +1629,17 @@ PyTypeObject KX_Scene::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_Scene::Parents[] = { + &KX_Scene::Type, &CValue::Type, - 0,0,0,0,0,0, - py_base_new + NULL }; PyMethodDef KX_Scene::Methods[] = { @@ -1652,7 +1654,7 @@ PyMethodDef KX_Scene::Methods[] = { PyObject* KX_Scene::pyattr_get_name(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) { KX_Scene* self= static_cast<KX_Scene*>(self_v); - return PyUnicode_FromString(self->GetName().ReadPtr()); + return PyString_FromString(self->GetName().ReadPtr()); } PyObject* KX_Scene::pyattr_get_objects(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef) @@ -1728,6 +1730,72 @@ PyAttributeDef KX_Scene::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_Scene::py_getattro__internal(PyObject *attr) +{ + py_getattro_up(PyObjectPlus); +} + +int KX_Scene::py_setattro__internal(PyObject *attr, PyObject *value) +{ + py_setattro_up(PyObjectPlus); +} + +PyObject* KX_Scene::py_getattro(PyObject *attr) +{ + PyObject *object = py_getattro__internal(attr); + + if (object==NULL) + { + PyErr_Clear(); + object = PyDict_GetItem(m_attr_dict, attr); + if(object) { + Py_INCREF(object); + } + else { + PyErr_Format(PyExc_AttributeError, "value = scene.myAttr: KX_Scene, attribute \"%s\" not found", PyString_AsString(attr)); + } + } + + return object; +} + +PyObject* KX_Scene::py_getattro_dict() { + //py_getattro_dict_up(PyObjectPlus); + + PyObject *dict= py_getattr_dict(PyObjectPlus::py_getattro_dict(), Type.tp_dict); + if(dict==NULL) + return NULL; + + /* normally just return this but KX_Scene has some more items */ + + PyDict_Update(dict, m_attr_dict); + return dict; +} + +int KX_Scene::py_setattro(PyObject *attr, PyObject *value) +{ + int ret= py_setattro__internal(attr, value); + + if (ret==PY_SET_ATTR_MISSING) { + if (PyDict_SetItem(m_attr_dict, attr, value)==0) { + PyErr_Clear(); + ret= PY_SET_ATTR_SUCCESS; + } + else { + PyErr_SetString(PyExc_AttributeError, "scene.UserAttr = value: KX_Scenes, failed assigning value to internal dictionary"); + ret= PY_SET_ATTR_FAIL; + } + } + + return ret; +} + +int KX_Scene::py_delattro(PyObject *attr) +{ + PyDict_DelItem(m_attr_dict, attr); + return 0; +} + KX_PYMETHODDEF_DOC_NOARGS(KX_Scene, getLightList, "getLightList() -> list [KX_Light]\n" "Returns a list of all lights in the scene.\n" @@ -1752,7 +1820,7 @@ KX_PYMETHODDEF_DOC_NOARGS(KX_Scene, getName, ) { ShowDeprecationWarning("getName()", "the name property"); - return PyUnicode_FromString(GetName()); + return PyString_FromString(GetName()); } KX_PYMETHODDEF_DOC(KX_Scene, addObject, diff --git a/source/gameengine/Ketsji/KX_Scene.h b/source/gameengine/Ketsji/KX_Scene.h index 2792f1f5fe4..79d3f7fd828 100644 --- a/source/gameengine/Ketsji/KX_Scene.h +++ b/source/gameengine/Ketsji/KX_Scene.h @@ -563,7 +563,15 @@ public: static PyObject* pyattr_get_active_camera(void* self_v, const KX_PYATTRIBUTE_DEF *attrdef); static int pyattr_set_active_camera(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value); - virtual PyObject* py_repr(void) { return PyUnicode_FromString(GetName().ReadPtr()); } + virtual PyObject* py_getattro(PyObject *attr); /* name, active_camera, gravity, suspended, viewport, framing, activity_culling, activity_culling_radius */ + virtual PyObject* py_getattro_dict(); + + virtual int py_setattro(PyObject *attr, PyObject *value); + virtual int py_delattro(PyObject *attr); + virtual PyObject* py_repr(void) { return PyString_FromString(GetName().ReadPtr()); } + + PyObject* py_getattro__internal(PyObject *attr); + int py_setattro__internal(PyObject *attr, PyObject *pyvalue); /** * Sets the time the scene was suspended diff --git a/source/gameengine/Ketsji/KX_SceneActuator.cpp b/source/gameengine/Ketsji/KX_SceneActuator.cpp index 5528e58ef77..1b790ec9824 100644 --- a/source/gameengine/Ketsji/KX_SceneActuator.cpp +++ b/source/gameengine/Ketsji/KX_SceneActuator.cpp @@ -49,8 +49,9 @@ KX_SceneActuator::KX_SceneActuator(SCA_IObject *gameobj, KX_Scene *scene, KX_KetsjiEngine* ketsjiEngine, const STR_String& nextSceneName, - KX_Camera* camera) - : SCA_IActuator(gameobj) + KX_Camera* camera, + PyTypeObject* T) + : SCA_IActuator(gameobj, T) { m_mode = mode; m_scene = scene; @@ -133,7 +134,7 @@ bool KX_SceneActuator::Update() { // if no camera is set and the parent object is a camera, use it as the camera SCA_IObject* parent = GetParent(); - if (parent->GetGameObjectType()==SCA_IObject::OBJ_CAMERA) + if (parent->isA(&KX_Camera::Type)) { m_scene->SetActiveCamera((KX_Camera*)parent); } @@ -238,17 +239,26 @@ PyTypeObject KX_SceneActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + + +PyParentObject KX_SceneActuator::Parents[] = +{ + &KX_SceneActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; + + PyMethodDef KX_SceneActuator::Methods[] = { //Deprecated functions ------> @@ -270,6 +280,20 @@ PyAttributeDef KX_SceneActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_SceneActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_SceneActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_SceneActuator::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_IActuator); +} + PyObject* KX_SceneActuator::pyattr_get_camera(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef) { KX_SceneActuator* actuator = static_cast<KX_SceneActuator*>(self); @@ -331,7 +355,7 @@ const char KX_SceneActuator::GetUseRestart_doc[] = PyObject* KX_SceneActuator::PyGetUseRestart() { ShowDeprecationWarning("getUseRestart()", "the useRestart property"); - return PyLong_FromSsize_t(!(m_restart == 0)); + return PyInt_FromLong(!(m_restart == 0)); } @@ -367,7 +391,7 @@ const char KX_SceneActuator::GetScene_doc[] = PyObject* KX_SceneActuator::PyGetScene() { ShowDeprecationWarning("getScene()", "the scene property"); - return PyUnicode_FromString(m_nextSceneName); + return PyString_FromString(m_nextSceneName); } @@ -408,7 +432,7 @@ PyObject* KX_SceneActuator::PyGetCamera() { ShowDeprecationWarning("getCamera()", "the camera property"); if (m_camera) { - return PyUnicode_FromString(m_camera->GetName()); + return PyString_FromString(m_camera->GetName()); } else { Py_RETURN_NONE; diff --git a/source/gameengine/Ketsji/KX_SceneActuator.h b/source/gameengine/Ketsji/KX_SceneActuator.h index 86de3395d1e..2412dd02590 100644 --- a/source/gameengine/Ketsji/KX_SceneActuator.h +++ b/source/gameengine/Ketsji/KX_SceneActuator.h @@ -77,7 +77,8 @@ class KX_SceneActuator : public SCA_IActuator KX_Scene* scene, KX_KetsjiEngine* ketsjiEngine, const STR_String& nextSceneName, - KX_Camera* camera); + KX_Camera* camera, + PyTypeObject* T=&Type); virtual ~KX_SceneActuator(); virtual CValue* GetReplica(); @@ -91,6 +92,10 @@ class KX_SceneActuator : public SCA_IActuator /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + /* 1. set */ /* Removed */ diff --git a/source/gameengine/Ketsji/KX_SoundActuator.cpp b/source/gameengine/Ketsji/KX_SoundActuator.cpp index 673f42283dd..c13271f66a5 100644 --- a/source/gameengine/Ketsji/KX_SoundActuator.cpp +++ b/source/gameengine/Ketsji/KX_SoundActuator.cpp @@ -50,8 +50,9 @@ KX_SoundActuator::KX_SoundActuator(SCA_IObject* gameobj, SND_Scene* sndscene, KX_SOUNDACT_TYPE type, short start, - short end) - : SCA_IActuator(gameobj) + short end, + PyTypeObject* T) + : SCA_IActuator(gameobj,T) { m_soundObject = sndobj; m_soundScene = sndscene; @@ -249,17 +250,25 @@ PyTypeObject KX_SoundActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + + + +PyParentObject KX_SoundActuator::Parents[] = { + &KX_SoundActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; + + PyMethodDef KX_SoundActuator::Methods[] = { // Deprecated -----> {"setFilename", (PyCFunction) KX_SoundActuator::sPySetFilename, METH_VARARGS,NULL}, @@ -331,13 +340,25 @@ KX_PYMETHODDEF_DOC_NOARGS(KX_SoundActuator, stopSound, } /* Atribute setting and getting -------------------------------------------- */ +PyObject* KX_SoundActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_SoundActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_SoundActuator::py_setattro(PyObject *attr, PyObject* value) { + py_setattro_up(SCA_IActuator); +} PyObject* KX_SoundActuator::pyattr_get_filename(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef) { KX_SoundActuator * actuator = static_cast<KX_SoundActuator *> (self); if (!actuator->m_soundObject) { - return PyUnicode_FromString(""); + return PyString_FromString(""); } STR_String objectname = actuator->m_soundObject->GetObjectName(); char* name = objectname.Ptr(); @@ -346,7 +367,7 @@ PyObject* KX_SoundActuator::pyattr_get_filename(void *self, const struct KX_PYAT PyErr_SetString(PyExc_RuntimeError, "value = actuator.fileName: KX_SoundActuator, unable to get sound fileName"); return NULL; } else - return PyUnicode_FromString(name); + return PyString_FromString(name); } PyObject* KX_SoundActuator::pyattr_get_gain(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef) @@ -381,7 +402,7 @@ PyObject* KX_SoundActuator::pyattr_get_looping(void *self, const struct KX_PYATT { KX_SoundActuator * actuator = static_cast<KX_SoundActuator *> (self); int looping = (actuator->m_soundObject) ? actuator->m_soundObject->GetLoopMode() : (int)SND_LOOP_OFF; - PyObject* result = PyLong_FromSsize_t(looping); + PyObject* result = PyInt_FromLong(looping); return result; } @@ -559,7 +580,7 @@ PyObject* KX_SoundActuator::PyGetFilename() ShowDeprecationWarning("getFilename()", "the fileName property"); if (!m_soundObject) { - return PyUnicode_FromString(""); + return PyString_FromString(""); } STR_String objectname = m_soundObject->GetObjectName(); char* name = objectname.Ptr(); @@ -568,7 +589,7 @@ PyObject* KX_SoundActuator::PyGetFilename() PyErr_SetString(PyExc_RuntimeError, "Unable to get sound fileName"); return NULL; } else - return PyUnicode_FromString(name); + return PyString_FromString(name); } PyObject* KX_SoundActuator::PySetGain(PyObject* args) @@ -668,7 +689,7 @@ PyObject* KX_SoundActuator::PyGetLooping() { ShowDeprecationWarning("getLooping()", "the looping property"); int looping = (m_soundObject) ? m_soundObject->GetLoopMode() : (int)SND_LOOP_OFF; - PyObject* result = PyLong_FromSsize_t(looping); + PyObject* result = PyInt_FromLong(looping); return result; } @@ -756,7 +777,7 @@ PyObject* KX_SoundActuator::PySetType(PyObject* args) PyObject* KX_SoundActuator::PyGetType() { ShowDeprecationWarning("getType()", "the mode property"); - return PyLong_FromSsize_t(m_type); + return PyInt_FromLong(m_type); } // <----- diff --git a/source/gameengine/Ketsji/KX_SoundActuator.h b/source/gameengine/Ketsji/KX_SoundActuator.h index adafee0a30b..a7491355667 100644 --- a/source/gameengine/Ketsji/KX_SoundActuator.h +++ b/source/gameengine/Ketsji/KX_SoundActuator.h @@ -66,7 +66,8 @@ public: class SND_Scene* sndscene, KX_SOUNDACT_TYPE type, short start, - short end); + short end, + PyTypeObject* T=&Type); ~KX_SoundActuator(); @@ -80,6 +81,10 @@ public: /* Python interface --------------------------------------------------- */ /* -------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); + KX_PYMETHOD_DOC_NOARGS(KX_SoundActuator, startSound); KX_PYMETHOD_DOC_NOARGS(KX_SoundActuator, pauseSound); KX_PYMETHOD_DOC_NOARGS(KX_SoundActuator, stopSound); diff --git a/source/gameengine/Ketsji/KX_StateActuator.cpp b/source/gameengine/Ketsji/KX_StateActuator.cpp index 9815d6274aa..f6979eee0f4 100644 --- a/source/gameengine/Ketsji/KX_StateActuator.cpp +++ b/source/gameengine/Ketsji/KX_StateActuator.cpp @@ -38,9 +38,10 @@ KX_StateActuator::KX_StateActuator( SCA_IObject* gameobj, int operation, - unsigned int mask + unsigned int mask, + PyTypeObject* T ) - : SCA_IActuator(gameobj), + : SCA_IActuator(gameobj,T), m_operation(operation), m_mask(mask) { @@ -153,18 +154,24 @@ PyTypeObject KX_StateActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject +KX_StateActuator::Parents[] = { + &KX_StateActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; -PyMethodDef KX_StateActuator::Methods[] = { +PyMethodDef +KX_StateActuator::Methods[] = { // deprecated --> {"setOperation", (PyCFunction) KX_StateActuator::sPySetOperation, METH_VARARGS, (PY_METHODCHAR)SetOperation_doc}, @@ -180,6 +187,20 @@ PyAttributeDef KX_StateActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_StateActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_StateActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_StateActuator::py_setattro(PyObject *attr, PyObject* value) +{ + py_setattro_up(SCA_IActuator); +} + /* set operation ---------------------------------------------------------- */ const char diff --git a/source/gameengine/Ketsji/KX_StateActuator.h b/source/gameengine/Ketsji/KX_StateActuator.h index ce86c4b44fe..a4191a4c5fd 100644 --- a/source/gameengine/Ketsji/KX_StateActuator.h +++ b/source/gameengine/Ketsji/KX_StateActuator.h @@ -66,8 +66,9 @@ class KX_StateActuator : public SCA_IActuator KX_StateActuator( SCA_IObject* gameobj, int operation, - unsigned int mask - ); + unsigned int mask, + PyTypeObject* T=&Type + ); virtual ~KX_StateActuator( @@ -88,6 +89,10 @@ class KX_StateActuator : public SCA_IActuator /* --------------------------------------------------------------------- */ /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); //KX_PYMETHOD_DOC KX_PYMETHOD_DOC_VARARGS(KX_StateActuator,SetOperation); KX_PYMETHOD_DOC_VARARGS(KX_StateActuator,SetMask); diff --git a/source/gameengine/Ketsji/KX_SumoPhysicsController.cpp b/source/gameengine/Ketsji/KX_SumoPhysicsController.cpp new file mode 100644 index 00000000000..fc053f05e63 --- /dev/null +++ b/source/gameengine/Ketsji/KX_SumoPhysicsController.cpp @@ -0,0 +1,244 @@ +#include "KX_ConvertPhysicsObject.h" + +#ifdef USE_SUMO_SOLID + +#ifdef WIN32 +#pragma warning (disable : 4786) +#endif + +#include "KX_SumoPhysicsController.h" +#include "SG_Spatial.h" +#include "SM_Scene.h" +#include "KX_GameObject.h" +#include "KX_MotionState.h" +#include "KX_ClientObjectInfo.h" + +#include "PHY_IPhysicsEnvironment.h" + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +void KX_SumoPhysicsController::applyImpulse(const MT_Point3& attach, const MT_Vector3& impulse) +{ + SumoPhysicsController::applyImpulse(attach[0],attach[1],attach[2],impulse[0],impulse[1],impulse[2]); +} +void KX_SumoPhysicsController::RelativeTranslate(const MT_Vector3& dloc,bool local) +{ + SumoPhysicsController::RelativeTranslate(dloc[0],dloc[1],dloc[2],local); + +} +void KX_SumoPhysicsController::RelativeRotate(const MT_Matrix3x3& drot,bool local) +{ + float oldmat[12]; + drot.getValue(oldmat); +/* float newmat[9]; + float *m = &newmat[0]; + double *orgm = &oldmat[0]; + + *m++ = *orgm++;*m++ = *orgm++;*m++ = *orgm++;orgm++; + *m++ = *orgm++;*m++ = *orgm++;*m++ = *orgm++;orgm++; + *m++ = *orgm++;*m++ = *orgm++;*m++ = *orgm++;orgm++; */ + + SumoPhysicsController::RelativeRotate(oldmat,local); +} + +void KX_SumoPhysicsController::SetLinearVelocity(const MT_Vector3& lin_vel,bool local) +{ + SumoPhysicsController::SetLinearVelocity(lin_vel[0],lin_vel[1],lin_vel[2],local); + +} + +void KX_SumoPhysicsController::SetAngularVelocity(const MT_Vector3& ang_vel,bool local) +{ + SumoPhysicsController::SetAngularVelocity(ang_vel[0],ang_vel[1],ang_vel[2],local); +} + +MT_Vector3 KX_SumoPhysicsController::GetVelocity(const MT_Point3& pos) +{ + + float linvel[3]; + SumoPhysicsController::GetVelocity(pos[0],pos[1],pos[2],linvel[0],linvel[1],linvel[2]); + + return MT_Vector3 (linvel); +} + +MT_Vector3 KX_SumoPhysicsController::GetLinearVelocity() +{ + return GetVelocity(MT_Point3(0,0,0)); + +} + +void KX_SumoPhysicsController::resolveCombinedVelocities(float linvelX,float linvelY,float linvelZ,float angVelX,float angVelY,float angVelZ) +{ + SumoPhysicsController::resolveCombinedVelocities(linvelX,linvelY,linvelZ,angVelX,angVelY,angVelZ); +} + +void KX_SumoPhysicsController::ApplyTorque(const MT_Vector3& torque,bool local) +{ + SumoPhysicsController::ApplyTorque(torque[0],torque[1],torque[2],local); + +} + +void KX_SumoPhysicsController::ApplyForce(const MT_Vector3& force,bool local) +{ + SumoPhysicsController::ApplyForce(force[0],force[1],force[2],local); +} + +bool KX_SumoPhysicsController::Update(double time) +{ + return SynchronizeMotionStates(time); +} + +void KX_SumoPhysicsController::SetSimulatedTime(double time) +{ + +} + +void KX_SumoPhysicsController::SetSumoTransform(bool nondynaonly) +{ + SumoPhysicsController::setSumoTransform(nondynaonly); + +} + +void KX_SumoPhysicsController::SuspendDynamics(bool) +{ + SumoPhysicsController::SuspendDynamics(); +} + +void KX_SumoPhysicsController::RestoreDynamics() +{ + SumoPhysicsController::RestoreDynamics(); +} + +SG_Controller* KX_SumoPhysicsController::GetReplica(SG_Node* destnode) +{ + + PHY_IMotionState* motionstate = new KX_MotionState(destnode); + + KX_SumoPhysicsController* physicsreplica = new KX_SumoPhysicsController(*this); + + //parentcontroller is here be able to avoid collisions between parent/child + + PHY_IPhysicsController* parentctrl = NULL; + + if (destnode != destnode->GetRootSGParent()) + { + KX_GameObject* clientgameobj = (KX_GameObject*) destnode->GetRootSGParent()->GetSGClientObject(); + if (clientgameobj) + { + parentctrl = (KX_SumoPhysicsController*)clientgameobj->GetPhysicsController(); + } else + { + // it could be a false node, try the children + NodeList::const_iterator childit; + for ( + childit = destnode->GetSGChildren().begin(); + childit!= destnode->GetSGChildren().end(); + ++childit + ) { + KX_GameObject *clientgameobj = static_cast<KX_GameObject*>( (*childit)->GetSGClientObject()); + if (clientgameobj) + { + parentctrl = (KX_SumoPhysicsController*)clientgameobj->GetPhysicsController(); + } + } + } + } + + physicsreplica->PostProcessReplica(motionstate,parentctrl); + + return physicsreplica; +} + + +void KX_SumoPhysicsController::SetObject (SG_IObject* object) +{ + SG_Controller::SetObject(object); + + // cheating here... +//should not be necessary, is it for duplicates ? + +KX_GameObject* gameobj = (KX_GameObject*) object->GetSGClientObject(); +gameobj->SetPhysicsController(this,gameobj->IsDynamic()); +GetSumoObject()->setClientObject(gameobj->getClientInfo()); +} + +void KX_SumoPhysicsController::setMargin(float collisionMargin) +{ + SumoPhysicsController::SetMargin(collisionMargin); +} + + +void KX_SumoPhysicsController::setOrientation(const MT_Matrix3x3& rot) +{ + MT_Quaternion orn = rot.getRotation(); + SumoPhysicsController::setOrientation( + orn[0],orn[1],orn[2],orn[3]); + +} +void KX_SumoPhysicsController::getOrientation(MT_Quaternion& orn) +{ + + float quat[4]; + + SumoPhysicsController::getOrientation(quat[0],quat[1],quat[2],quat[3]); + + orn = MT_Quaternion(quat); + +} + +void KX_SumoPhysicsController::setPosition(const MT_Point3& pos) +{ + SumoPhysicsController::setPosition(pos[0],pos[1],pos[2]); + +} + +void KX_SumoPhysicsController::setScaling(const MT_Vector3& scaling) +{ + SumoPhysicsController::setScaling(scaling[0],scaling[1],scaling[2]); + +} + +MT_Scalar KX_SumoPhysicsController::GetMass() +{ + return SumoPhysicsController::getMass(); +} + +void KX_SumoPhysicsController::SetMass(MT_Scalar newmass) +{ +} + +MT_Vector3 KX_SumoPhysicsController::GetLocalInertia() +{ + return MT_Vector3(0.f, 0.f, 0.f); // \todo +} + +MT_Scalar KX_SumoPhysicsController::GetRadius() +{ + return SumoPhysicsController::GetRadius(); +} + +MT_Vector3 KX_SumoPhysicsController::getReactionForce() +{ + float force[3]; + SumoPhysicsController::getReactionForce(force[0],force[1],force[2]); + return MT_Vector3(force); + +} + +void KX_SumoPhysicsController::setRigidBody(bool rigid) +{ + SumoPhysicsController::setRigidBody(rigid); + +} + + +KX_SumoPhysicsController::~KX_SumoPhysicsController() +{ + + +} + + +#endif//USE_SUMO_SOLID diff --git a/source/gameengine/Ketsji/KX_SumoPhysicsController.h b/source/gameengine/Ketsji/KX_SumoPhysicsController.h new file mode 100644 index 00000000000..278994c6ae7 --- /dev/null +++ b/source/gameengine/Ketsji/KX_SumoPhysicsController.h @@ -0,0 +1,122 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef __KX_SUMOPHYSICSCONTROLLER_H +#define __KX_SUMOPHYSICSCONTROLLER_H + +#include "PHY_IPhysicsController.h" + +/** + Physics Controller, a special kind of Scene Graph Transformation Controller. + It get's callbacks from Sumo in case a transformation change took place. + Each time the scene graph get's updated, the controller get's a chance + in the 'Update' method to reflect changed. +*/ + +#include "SumoPhysicsController.h" +#include "KX_IPhysicsController.h" + +class KX_SumoPhysicsController : public KX_IPhysicsController, + public SumoPhysicsController + +{ + + +public: + KX_SumoPhysicsController( + class SM_Scene* sumoScene, + class SM_Object* sumoObj, + class PHY_IMotionState* motionstate + ,bool dyna) + : KX_IPhysicsController(dyna,false,false,NULL) , + SumoPhysicsController(sumoScene,/*solidscene,*/sumoObj,motionstate,dyna) + { + }; + virtual ~KX_SumoPhysicsController(); + + void applyImpulse(const MT_Point3& attach, const MT_Vector3& impulse); + virtual void SetObject (SG_IObject* object); + virtual void setMargin (float collisionMargin); + + void RelativeTranslate(const MT_Vector3& dloc,bool local); + void RelativeRotate(const MT_Matrix3x3& drot,bool local); + void ApplyTorque(const MT_Vector3& torque,bool local); + void ApplyForce(const MT_Vector3& force,bool local); + MT_Vector3 GetLinearVelocity(); + MT_Vector3 GetAngularVelocity() // to keep compiler happy + { return MT_Vector3(0.0,0.0,0.0); } + MT_Vector3 GetVelocity(const MT_Point3& pos); + void SetAngularVelocity(const MT_Vector3& ang_vel,bool local); + void SetLinearVelocity(const MT_Vector3& lin_vel,bool local); + void resolveCombinedVelocities(float linvelX,float linvelY,float linvelZ,float angVelX,float angVelY,float angVelZ); + + + void SuspendDynamics(bool); + void RestoreDynamics(); + virtual void AddCompoundChild(KX_IPhysicsController* child) { } + virtual void RemoveCompoundChild(KX_IPhysicsController* child) { } + + virtual void getOrientation(MT_Quaternion& orn); + virtual void setOrientation(const MT_Matrix3x3& orn); + virtual void SetTransform() {} + + virtual void setPosition(const MT_Point3& pos); + virtual void setScaling(const MT_Vector3& scaling); + virtual MT_Scalar GetMass(); + virtual void SetMass(MT_Scalar newmass); + virtual MT_Vector3 GetLocalInertia(); + virtual MT_Scalar GetRadius(); + virtual MT_Vector3 getReactionForce(); + virtual void setRigidBody(bool rigid); + + virtual float GetLinVelocityMin() { return SumoPhysicsController::GetLinVelocityMin(); } + virtual void SetLinVelocityMin(float val) { SumoPhysicsController::SetLinVelocityMin(val); } + virtual float GetLinVelocityMax() { return SumoPhysicsController::GetLinVelocityMax(); } + virtual void SetLinVelocityMax(float val) { SumoPhysicsController::SetLinVelocityMax(val); } + + virtual SG_Controller* GetReplica(class SG_Node* destnode); + + + void SetSumoTransform(bool nondynaonly); + // todo: remove next line ! + virtual void SetSimulatedTime(double time); + + // call from scene graph to update + virtual bool Update(double time); + + void + SetOption( + int option, + int value + ){ + // intentionally empty + }; +}; + +#endif //__KX_SUMOPHYSICSCONTROLLER_H + diff --git a/source/gameengine/Ketsji/KX_TouchSensor.cpp b/source/gameengine/Ketsji/KX_TouchSensor.cpp index b0cf172c27a..c06acd4a873 100644 --- a/source/gameengine/Ketsji/KX_TouchSensor.cpp +++ b/source/gameengine/Ketsji/KX_TouchSensor.cpp @@ -97,8 +97,8 @@ bool KX_TouchSensor::Evaluate() return result; } -KX_TouchSensor::KX_TouchSensor(SCA_EventManager* eventmgr,KX_GameObject* gameobj,bool bFindMaterial,bool bTouchPulse,const STR_String& touchedpropname) -:SCA_ISensor(gameobj,eventmgr), +KX_TouchSensor::KX_TouchSensor(SCA_EventManager* eventmgr,KX_GameObject* gameobj,bool bFindMaterial,bool bTouchPulse,const STR_String& touchedpropname,PyTypeObject* T) +:SCA_ISensor(gameobj,eventmgr,T), m_touchedpropname(touchedpropname), m_bFindMaterial(bFindMaterial), m_bTouchPulse(bTouchPulse), @@ -310,15 +310,19 @@ PyTypeObject KX_TouchSensor::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_TouchSensor::Parents[] = { + &KX_TouchSensor::Type, &SCA_ISensor::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; PyMethodDef KX_TouchSensor::Methods[] = { @@ -344,6 +348,20 @@ PyAttributeDef KX_TouchSensor::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_TouchSensor::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_ISensor); +} + +PyObject* KX_TouchSensor::py_getattro_dict() { + py_getattro_dict_up(SCA_ISensor); +} + +int KX_TouchSensor::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_ISensor); +} + /* Python API */ /* 1. setProperty */ @@ -356,7 +374,7 @@ const char KX_TouchSensor::SetProperty_doc[] = PyObject* KX_TouchSensor::PySetProperty(PyObject* value) { ShowDeprecationWarning("setProperty()", "the propName property"); - char *nameArg= _PyUnicode_AsString(value); + char *nameArg= PyString_AsString(value); if (nameArg==NULL) { PyErr_SetString(PyExc_ValueError, "expected a "); return NULL; @@ -374,7 +392,7 @@ const char KX_TouchSensor::GetProperty_doc[] = PyObject* KX_TouchSensor::PyGetProperty() { ShowDeprecationWarning("getProperty()", "the propName property"); - return PyUnicode_FromString(m_touchedpropname); + return PyString_FromString(m_touchedpropname); } const char KX_TouchSensor::GetHitObject_doc[] = @@ -415,7 +433,7 @@ const char KX_TouchSensor::GetTouchMaterial_doc[] = PyObject* KX_TouchSensor::PyGetTouchMaterial() { ShowDeprecationWarning("getTouchMaterial()", "the useMaterial property"); - return PyLong_FromSsize_t(m_bFindMaterial); + return PyInt_FromLong(m_bFindMaterial); } /* 6. setTouchMaterial */ @@ -428,7 +446,7 @@ const char KX_TouchSensor::SetTouchMaterial_doc[] = PyObject* KX_TouchSensor::PySetTouchMaterial(PyObject *value) { ShowDeprecationWarning("setTouchMaterial()", "the useMaterial property"); - int pulseArg = PyLong_AsSsize_t(value); + int pulseArg = PyInt_AsLong(value); if(pulseArg ==-1 && PyErr_Occurred()) { PyErr_SetString(PyExc_ValueError, "expected a bool"); diff --git a/source/gameengine/Ketsji/KX_TouchSensor.h b/source/gameengine/Ketsji/KX_TouchSensor.h index 6cbf5b15e3b..476c63e89db 100644 --- a/source/gameengine/Ketsji/KX_TouchSensor.h +++ b/source/gameengine/Ketsji/KX_TouchSensor.h @@ -79,7 +79,8 @@ public: class KX_GameObject* gameobj, bool bFindMaterial, bool bTouchPulse, - const STR_String& touchedpropname) ; + const STR_String& touchedpropname, + PyTypeObject* T=&Type) ; virtual ~KX_TouchSensor(); virtual CValue* GetReplica(); @@ -120,6 +121,10 @@ public: /* --------------------------------------------------------------------- */ /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); //Deprecated -----> /* 1. setProperty */ diff --git a/source/gameengine/Ketsji/KX_TrackToActuator.cpp b/source/gameengine/Ketsji/KX_TrackToActuator.cpp index e8a06d8d619..5a50d0fb944 100644 --- a/source/gameengine/Ketsji/KX_TrackToActuator.cpp +++ b/source/gameengine/Ketsji/KX_TrackToActuator.cpp @@ -59,8 +59,10 @@ KX_TrackToActuator::KX_TrackToActuator(SCA_IObject *gameobj, int time, bool allow3D, int trackflag, - int upflag) - : SCA_IActuator(gameobj) + int upflag, + PyTypeObject* T) + : + SCA_IActuator(gameobj, T) { m_time = time; m_allow3D = allow3D; @@ -72,6 +74,7 @@ KX_TrackToActuator::KX_TrackToActuator(SCA_IObject *gameobj, if (m_object) m_object->RegisterActuator(this); + if (gameobj->isA(&KX_GameObject::Type)) { // if the object is vertex parented, don't check parent orientation as the link is broken if (!((KX_GameObject*)gameobj)->IsVertexParent()){ @@ -447,17 +450,25 @@ PyTypeObject KX_TrackToActuator::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &SCA_IActuator::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods }; + + +PyParentObject KX_TrackToActuator::Parents[] = { + &KX_TrackToActuator::Type, + &SCA_IActuator::Type, + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL +}; + + + PyMethodDef KX_TrackToActuator::Methods[] = { // ---> deprecated {"setTime", (PyCFunction) KX_TrackToActuator::sPySetTime, METH_VARARGS, (PY_METHODCHAR)SetTime_doc}, @@ -507,6 +518,20 @@ int KX_TrackToActuator::pyattr_set_object(void *self, const struct KX_PYATTRIBUT } +PyObject* KX_TrackToActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_TrackToActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_TrackToActuator::py_setattro(PyObject *attr, PyObject* value) +{ + py_setattro_up(SCA_IActuator); +} + /* 1. setObject */ const char KX_TrackToActuator::SetObject_doc[] = "setObject(object)\n" @@ -551,7 +576,7 @@ PyObject* KX_TrackToActuator::PyGetObject(PyObject* args) Py_RETURN_NONE; if (ret_name_only) - return PyUnicode_FromString(m_object->GetName()); + return PyString_FromString(m_object->GetName()); else return m_object->GetProxy(); } @@ -588,7 +613,7 @@ const char KX_TrackToActuator::GetTime_doc[] = PyObject* KX_TrackToActuator::PyGetTime() { ShowDeprecationWarning("getTime()", "the timer property"); - return PyLong_FromSsize_t(m_time); + return PyInt_FromLong(m_time); } @@ -600,7 +625,7 @@ const char KX_TrackToActuator::GetUse3D_doc[] = PyObject* KX_TrackToActuator::PyGetUse3D() { ShowDeprecationWarning("setTime()", "the use3D property"); - return PyLong_FromSsize_t(!(m_allow3D == 0)); + return PyInt_FromLong(!(m_allow3D == 0)); } diff --git a/source/gameengine/Ketsji/KX_TrackToActuator.h b/source/gameengine/Ketsji/KX_TrackToActuator.h index 801e695bb9b..c4cc2b1f062 100644 --- a/source/gameengine/Ketsji/KX_TrackToActuator.h +++ b/source/gameengine/Ketsji/KX_TrackToActuator.h @@ -56,7 +56,7 @@ class KX_TrackToActuator : public SCA_IActuator public: KX_TrackToActuator(SCA_IObject* gameobj, SCA_IObject *ob, int time, - bool threedee,int trackflag,int upflag); + bool threedee,int trackflag,int upflag, PyTypeObject* T=&Type); virtual ~KX_TrackToActuator(); virtual CValue* GetReplica() { KX_TrackToActuator* replica = new KX_TrackToActuator(*this); @@ -70,6 +70,9 @@ class KX_TrackToActuator : public SCA_IActuator virtual bool Update(double curtime, bool frame); /* Python part */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject* value); /* These are used to get and set m_ob */ static PyObject* pyattr_get_object(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef); diff --git a/source/gameengine/Ketsji/KX_VehicleWrapper.cpp b/source/gameengine/Ketsji/KX_VehicleWrapper.cpp index 7001bfc8b7e..8146d04a878 100644 --- a/source/gameengine/Ketsji/KX_VehicleWrapper.cpp +++ b/source/gameengine/Ketsji/KX_VehicleWrapper.cpp @@ -16,8 +16,8 @@ KX_VehicleWrapper::KX_VehicleWrapper( PHY_IVehicle* vehicle, - PHY_IPhysicsEnvironment* physenv) : - PyObjectPlus(), + PHY_IPhysicsEnvironment* physenv,PyTypeObject *T) : + PyObjectPlus(T), m_vehicle(vehicle), m_physenv(physenv) { @@ -127,13 +127,13 @@ PyObject* KX_VehicleWrapper::PyGetWheelOrientationQuaternion(PyObject* args) PyObject* KX_VehicleWrapper::PyGetNumWheels(PyObject* args) { - return PyLong_FromSsize_t(m_vehicle->GetNumWheels()); + return PyInt_FromLong(m_vehicle->GetNumWheels()); } PyObject* KX_VehicleWrapper::PyGetConstraintId(PyObject* args) { - return PyLong_FromSsize_t(m_vehicle->GetUserConstraintId()); + return PyInt_FromLong(m_vehicle->GetUserConstraintId()); } @@ -264,7 +264,7 @@ PyObject* KX_VehicleWrapper::PySetSteeringValue(PyObject* args) PyObject* KX_VehicleWrapper::PyGetConstraintType(PyObject* args) { - return PyLong_FromSsize_t(m_vehicle->GetUserConstraintType()); + return PyInt_FromLong(m_vehicle->GetUserConstraintType()); } @@ -289,17 +289,35 @@ PyTypeObject KX_VehicleWrapper::Type = { 0, 0, py_base_repr, - 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, - &PyObjectPlus::Type, 0,0,0,0,0,0, - py_base_new + py_base_getattro, + py_base_setattro, + 0,0,0,0,0,0,0,0,0, + Methods }; +PyParentObject KX_VehicleWrapper::Parents[] = { + &KX_VehicleWrapper::Type, + &PyObjectPlus::Type, + NULL +}; + +PyObject* KX_VehicleWrapper::py_getattro(PyObject *attr) +{ + //here you can search for existing data members (like mass,friction etc.) + py_getattro_up(PyObjectPlus); +} + +PyObject* KX_VehicleWrapper::py_getattro_dict() { + py_getattro_dict_up(PyObjectPlus); +} + +int KX_VehicleWrapper::py_setattro(PyObject *attr,PyObject* value) +{ + py_setattro_up(PyObjectPlus); +}; + + PyMethodDef KX_VehicleWrapper::Methods[] = { {"addWheel",(PyCFunction) KX_VehicleWrapper::sPyAddWheel, METH_VARARGS}, {"getNumWheels",(PyCFunction) KX_VehicleWrapper::sPyGetNumWheels, METH_VARARGS}, diff --git a/source/gameengine/Ketsji/KX_VehicleWrapper.h b/source/gameengine/Ketsji/KX_VehicleWrapper.h index d7f2da5cd7c..c2b5e3d9251 100644 --- a/source/gameengine/Ketsji/KX_VehicleWrapper.h +++ b/source/gameengine/Ketsji/KX_VehicleWrapper.h @@ -12,11 +12,14 @@ class PHY_IMotionState; class KX_VehicleWrapper : public PyObjectPlus { Py_Header; + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); std::vector<PHY_IMotionState*> m_motionStates; public: - KX_VehicleWrapper(PHY_IVehicle* vehicle,class PHY_IPhysicsEnvironment* physenv); + KX_VehicleWrapper(PHY_IVehicle* vehicle,class PHY_IPhysicsEnvironment* physenv,PyTypeObject *T = &Type); virtual ~KX_VehicleWrapper (); int getConstraintId(); diff --git a/source/gameengine/Ketsji/KX_VertexProxy.cpp b/source/gameengine/Ketsji/KX_VertexProxy.cpp index cb8c891969d..4b0ad083473 100644 --- a/source/gameengine/Ketsji/KX_VertexProxy.cpp +++ b/source/gameengine/Ketsji/KX_VertexProxy.cpp @@ -53,15 +53,18 @@ PyTypeObject KX_VertexProxy::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods +}; + +PyParentObject KX_VertexProxy::Parents[] = { + &KX_VertexProxy::Type, &CValue::Type, - 0,0,0,0,0,0, - py_base_new + &PyObjectPlus::Type, + NULL }; PyMethodDef KX_VertexProxy::Methods[] = { @@ -82,38 +85,37 @@ PyMethodDef KX_VertexProxy::Methods[] = { PyAttributeDef KX_VertexProxy::Attributes[] = { //KX_PYATTRIBUTE_TODO("DummyProps"), - + KX_PYATTRIBUTE_DUMMY("x"), KX_PYATTRIBUTE_DUMMY("y"), KX_PYATTRIBUTE_DUMMY("z"), - + KX_PYATTRIBUTE_DUMMY("r"), KX_PYATTRIBUTE_DUMMY("g"), KX_PYATTRIBUTE_DUMMY("b"), KX_PYATTRIBUTE_DUMMY("a"), - + KX_PYATTRIBUTE_DUMMY("u"), KX_PYATTRIBUTE_DUMMY("v"), - + KX_PYATTRIBUTE_DUMMY("u2"), KX_PYATTRIBUTE_DUMMY("v2"), - + KX_PYATTRIBUTE_DUMMY("XYZ"), KX_PYATTRIBUTE_DUMMY("UV"), - + KX_PYATTRIBUTE_DUMMY("color"), KX_PYATTRIBUTE_DUMMY("colour"), - + KX_PYATTRIBUTE_DUMMY("normal"), - + { NULL } //Sentinel }; -#if 0 PyObject* KX_VertexProxy::py_getattro(PyObject *attr) { - char *attr_str= _PyUnicode_AsString(attr); + char *attr_str= PyString_AsString(attr); if (attr_str[1]=='\0') { // Group single letters // pos if (attr_str[0]=='x') @@ -139,8 +141,8 @@ KX_VertexProxy::py_getattro(PyObject *attr) if (attr_str[0]=='v') return PyFloat_FromDouble(m_vertex->getUV1()[1]); } - - + + if (!strcmp(attr_str, "XYZ")) return PyObjectFrom(MT_Vector3(m_vertex->getXYZ())); @@ -154,21 +156,22 @@ KX_VertexProxy::py_getattro(PyObject *attr) color /= 255.0; return PyObjectFrom(color); } - + if (!strcmp(attr_str, "normal")) { return PyObjectFrom(MT_Vector3(m_vertex->getNormal())); } - + py_getattro_up(CValue); } -#endif +PyObject* KX_VertexProxy::py_getattro_dict() { + py_getattro_dict_up(CValue); +} -#if 0 int KX_VertexProxy::py_setattro(PyObject *attr, PyObject *pyvalue) { - char *attr_str= _PyUnicode_AsString(attr); + char *attr_str= PyString_AsString(attr); if (PySequence_Check(pyvalue)) { if (!strcmp(attr_str, "XYZ")) @@ -182,7 +185,7 @@ int KX_VertexProxy::py_setattro(PyObject *attr, PyObject *pyvalue) } return PY_SET_ATTR_FAIL; } - + if (!strcmp(attr_str, "UV")) { MT_Point2 vec; @@ -194,7 +197,7 @@ int KX_VertexProxy::py_setattro(PyObject *attr, PyObject *pyvalue) } return PY_SET_ATTR_FAIL; } - + if (!strcmp(attr_str, "color") || !strcmp(attr_str, "colour")) { MT_Vector4 vec; @@ -206,7 +209,7 @@ int KX_VertexProxy::py_setattro(PyObject *attr, PyObject *pyvalue) } return PY_SET_ATTR_FAIL; } - + if (!strcmp(attr_str, "normal")) { MT_Vector3 vec; @@ -219,7 +222,7 @@ int KX_VertexProxy::py_setattro(PyObject *attr, PyObject *pyvalue) return PY_SET_ATTR_FAIL; } } - + if (PyFloat_Check(pyvalue)) { float val = PyFloat_AsDouble(pyvalue); @@ -232,7 +235,7 @@ int KX_VertexProxy::py_setattro(PyObject *attr, PyObject *pyvalue) m_mesh->SetMeshModified(true); return PY_SET_ATTR_SUCCESS; } - + if (!strcmp(attr_str, "y")) { pos.y() = val; @@ -240,7 +243,7 @@ int KX_VertexProxy::py_setattro(PyObject *attr, PyObject *pyvalue) m_mesh->SetMeshModified(true); return PY_SET_ATTR_SUCCESS; } - + if (!strcmp(attr_str, "z")) { pos.z() = val; @@ -248,7 +251,7 @@ int KX_VertexProxy::py_setattro(PyObject *attr, PyObject *pyvalue) m_mesh->SetMeshModified(true); return PY_SET_ATTR_SUCCESS; } - + // uv MT_Point2 uv = m_vertex->getUV1(); if (!strcmp(attr_str, "u")) @@ -284,7 +287,7 @@ int KX_VertexProxy::py_setattro(PyObject *attr, PyObject *pyvalue) m_mesh->SetMeshModified(true); return PY_SET_ATTR_SUCCESS; } - + // col unsigned int icol = *((const unsigned int *)m_vertex->getRGBA()); unsigned char *cp = (unsigned char*) &icol; @@ -318,10 +321,9 @@ int KX_VertexProxy::py_setattro(PyObject *attr, PyObject *pyvalue) return PY_SET_ATTR_SUCCESS; } } - + return CValue::py_setattro(attr, pyvalue); } -#endif KX_VertexProxy::KX_VertexProxy(KX_MeshProxy*mesh, RAS_TexVert* vertex) : m_vertex(vertex), @@ -337,7 +339,7 @@ KX_VertexProxy::~KX_VertexProxy() // stuff for cvalue related things CValue* KX_VertexProxy::Calc(VALUE_OPERATOR, CValue *) { return NULL;} -CValue* KX_VertexProxy::CalcFinal(VALUE_DATA_TYPE, VALUE_OPERATOR, CValue *) { return NULL;} +CValue* KX_VertexProxy::CalcFinal(VALUE_DATA_TYPE, VALUE_OPERATOR, CValue *) { return NULL;} STR_String sVertexName="vertex"; const STR_String & KX_VertexProxy::GetText() {return sVertexName;}; double KX_VertexProxy::GetNumber() { return -1;} @@ -346,7 +348,7 @@ void KX_VertexProxy::SetName(const char *) { }; CValue* KX_VertexProxy::GetReplica() { return NULL;} // stuff for python integration - + PyObject* KX_VertexProxy::PyGetXYZ() { return PyObjectFrom(MT_Point3(m_vertex->getXYZ())); @@ -357,7 +359,7 @@ PyObject* KX_VertexProxy::PySetXYZ(PyObject* value) MT_Point3 vec; if (!PyVecTo(value, vec)) return NULL; - + m_vertex->SetXYZ(vec); m_mesh->SetMeshModified(true); Py_RETURN_NONE; @@ -373,7 +375,7 @@ PyObject* KX_VertexProxy::PySetNormal(PyObject* value) MT_Vector3 vec; if (!PyVecTo(value, vec)) return NULL; - + m_vertex->SetNormal(vec); m_mesh->SetMeshModified(true); Py_RETURN_NONE; @@ -383,18 +385,18 @@ PyObject* KX_VertexProxy::PySetNormal(PyObject* value) PyObject* KX_VertexProxy::PyGetRGBA() { int *rgba = (int *) m_vertex->getRGBA(); - return PyLong_FromSsize_t(*rgba); + return PyInt_FromLong(*rgba); } PyObject* KX_VertexProxy::PySetRGBA(PyObject* value) { - if PyLong_Check(value) { - int rgba = PyLong_AsSsize_t(value); + if PyInt_Check(value) { + int rgba = PyInt_AsLong(value); m_vertex->SetRGBA(rgba); m_mesh->SetMeshModified(true); Py_RETURN_NONE; } - else { + else { MT_Vector4 vec; if (PyVecTo(value, vec)) { @@ -403,7 +405,7 @@ PyObject* KX_VertexProxy::PySetRGBA(PyObject* value) Py_RETURN_NONE; } } - + PyErr_SetString(PyExc_TypeError, "vert.setRGBA(value): KX_VertexProxy, expected a 4D vector or an int"); return NULL; } @@ -419,7 +421,7 @@ PyObject* KX_VertexProxy::PySetUV(PyObject* value) MT_Point2 vec; if (!PyVecTo(value, vec)) return NULL; - + m_vertex->SetUV(vec); m_mesh->SetMeshModified(true); Py_RETURN_NONE; @@ -434,14 +436,14 @@ PyObject* KX_VertexProxy::PySetUV2(PyObject* args) { MT_Point2 vec; unsigned int unit= RAS_TexVert::SECOND_UV; - + PyObject* list= NULL; if(!PyArg_ParseTuple(args, "O|i:setUV2", &list, &unit)) return NULL; - + if (!PyVecTo(list, vec)) return NULL; - + m_vertex->SetFlag((m_vertex->getFlag()|RAS_TexVert::SECOND_UV)); m_vertex->SetUnit(unit); m_vertex->SetUV2(vec); diff --git a/source/gameengine/Ketsji/KX_VertexProxy.h b/source/gameengine/Ketsji/KX_VertexProxy.h index 13c57e9f556..42db5fbc322 100644 --- a/source/gameengine/Ketsji/KX_VertexProxy.h +++ b/source/gameengine/Ketsji/KX_VertexProxy.h @@ -53,6 +53,9 @@ public: // stuff for python integration + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *pyvalue); KX_PYMETHOD_NOARGS(KX_VertexProxy,GetXYZ); KX_PYMETHOD_O(KX_VertexProxy,SetXYZ); diff --git a/source/gameengine/Ketsji/KX_VisibilityActuator.cpp b/source/gameengine/Ketsji/KX_VisibilityActuator.cpp index 3561ccde9d9..d848065ad73 100644 --- a/source/gameengine/Ketsji/KX_VisibilityActuator.cpp +++ b/source/gameengine/Ketsji/KX_VisibilityActuator.cpp @@ -39,9 +39,10 @@ KX_VisibilityActuator::KX_VisibilityActuator( SCA_IObject* gameobj, bool visible, bool occlusion, - bool recursive + bool recursive, + PyTypeObject* T ) - : SCA_IActuator(gameobj), + : SCA_IActuator(gameobj,T), m_visible(visible), m_occlusion(occlusion), m_recursive(recursive) @@ -107,18 +108,25 @@ PyTypeObject KX_VisibilityActuator::Type = { 0, 0, py_base_repr, + 0,0,0,0,0,0, + py_base_getattro, + py_base_setattro, 0,0,0,0,0,0,0,0,0, - Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, - 0,0,0,0,0,0,0, - Methods, - 0, - 0, + Methods + +}; + +PyParentObject +KX_VisibilityActuator::Parents[] = { + &KX_VisibilityActuator::Type, &SCA_IActuator::Type, - 0,0,0,0,0,0, - py_base_new + &SCA_ILogicBrick::Type, + &CValue::Type, + NULL }; -PyMethodDef KX_VisibilityActuator::Methods[] = { +PyMethodDef +KX_VisibilityActuator::Methods[] = { // Deprecated -----> {"set", (PyCFunction) KX_VisibilityActuator::sPySetVisible, METH_VARARGS, (PY_METHODCHAR) SetVisible_doc}, @@ -133,6 +141,21 @@ PyAttributeDef KX_VisibilityActuator::Attributes[] = { { NULL } //Sentinel }; +PyObject* KX_VisibilityActuator::py_getattro(PyObject *attr) +{ + py_getattro_up(SCA_IActuator); +} + +PyObject* KX_VisibilityActuator::py_getattro_dict() { + py_getattro_dict_up(SCA_IActuator); +} + +int KX_VisibilityActuator::py_setattro(PyObject *attr, PyObject *value) +{ + py_setattro_up(SCA_IActuator); +} + + /* set visibility ---------------------------------------------------------- */ const char KX_VisibilityActuator::SetVisible_doc[] = diff --git a/source/gameengine/Ketsji/KX_VisibilityActuator.h b/source/gameengine/Ketsji/KX_VisibilityActuator.h index 3ad50c6cea2..45aba50f645 100644 --- a/source/gameengine/Ketsji/KX_VisibilityActuator.h +++ b/source/gameengine/Ketsji/KX_VisibilityActuator.h @@ -48,7 +48,9 @@ class KX_VisibilityActuator : public SCA_IActuator SCA_IObject* gameobj, bool visible, bool occlusion, - bool recursive); + bool recursive, + PyTypeObject* T=&Type + ); virtual ~KX_VisibilityActuator( @@ -67,6 +69,10 @@ class KX_VisibilityActuator : public SCA_IActuator /* Python interface ---------------------------------------------------- */ /* --------------------------------------------------------------------- */ + virtual PyObject* py_getattro(PyObject *attr); + virtual PyObject* py_getattro_dict(); + virtual int py_setattro(PyObject *attr, PyObject *value); + // Deprecated -----> KX_PYMETHOD_DOC_VARARGS(KX_VisibilityActuator,SetVisible); // <----- diff --git a/source/gameengine/Ketsji/Makefile b/source/gameengine/Ketsji/Makefile index 8e91eb6ff9a..59b3ff178fb 100644 --- a/source/gameengine/Ketsji/Makefile +++ b/source/gameengine/Ketsji/Makefile @@ -44,7 +44,7 @@ CPPFLAGS += -I../../blender/python CPPFLAGS += -I../../blender/python/generic CPPFLAGS += -I$(NAN_STRING)/include CPPFLAGS += -I$(NAN_SOUNDSYSTEM)/include -CPPFLAGS += -I$(NAN_FUZZICS)/include -I$(NAN_MOTO)/include +CPPFLAGS += -I$(NAN_FUZZICS)/include -I$(NAN_SUMO) -I$(NAN_MOTO)/include CPPFLAGS += -I$(NAN_SOLID)/include CPPFLAGS += -I$(NAN_BULLET2)/include CPPFLAGS += -I../Rasterizer/RAS_OpenGLRasterizer @@ -54,11 +54,14 @@ CPPFLAGS += -I../../kernel/gen_system CPPFLAGS += -I../Network -IKXNetwork CPPFLAGS += -I../Physics/common CPPFLAGS += -I../Physics/Dummy +CPPFLAGS += -I../Physics/Sumo +CPPFLAGS += -I../Physics/BlOde CPPFLAGS += -I../Physics/Bullet CPPFLAGS += -I. CPPFLAGS += -I../Converter CPPFLAGS += -I../../blender/blenkernel CPPFLAGS += -I../../blender/blenlib +CPPFLAGS += -I../../blender/editors/include CPPFLAGS += -I../../blender/makesdna CPPFLAGS += -I../../blender/imbuf CPPFLAGS += -I../../blender/gpu diff --git a/source/gameengine/Ketsji/SConscript b/source/gameengine/Ketsji/SConscript index b09267b79ff..49dbacc8916 100644 --- a/source/gameengine/Ketsji/SConscript +++ b/source/gameengine/Ketsji/SConscript @@ -18,9 +18,16 @@ incs += ' #source/blender/blenkernel #source/blender #source/blender/editors/inc incs += ' #source/blender/makesdna #source/blender/python #source/gameengine/Rasterizer' incs += ' #source/gameengine/GameLogic #source/gameengine/Expressions #source/gameengine/Network' incs += ' #source/gameengine/SceneGraph #source/gameengine/Physics/common #source/gameengine/Physics/Bullet' -incs += ' #source/gameengine/Physics/Dummy' +incs += ' #source/gameengine/Physics/BlOde #source/gameengine/Physics/Dummy' incs += ' #source/blender/misc #source/blender/blenloader #extern/glew/include #source/blender/gpu' +if env['WITH_BF_SOLID']: + incs += ' #source/gameengine/Physics/Sumo #source/gameengine/Physics/Sumo/include' + incs += ' #source/gameengine/Physics/Sumo/Fuzzics/include #source/gameengine/Network/LoopBackNetwork' + incs += ' ' + env['BF_SOLID_INC'] + defs += ' USE_SUMO_SOLID' + + incs += ' ' + env['BF_PYTHON_INC'] incs += ' ' + env['BF_BULLET_INC'] incs += ' ' + env['BF_OPENGL_INC'] diff --git a/source/gameengine/Physics/BlOde/Makefile b/source/gameengine/Physics/BlOde/Makefile new file mode 100644 index 00000000000..1fbbf198377 --- /dev/null +++ b/source/gameengine/Physics/BlOde/Makefile @@ -0,0 +1,48 @@ +# +# $Id$ +# +# ***** BEGIN GPL LICENSE BLOCK ***** +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software Foundation, +# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. +# All rights reserved. +# +# The Original Code is: all of this file. +# +# Contributor(s): none yet. +# +# ***** END GPL LICENSE BLOCK ***** +# +# + +LIBNAME = blode +DIR = $(OCGDIR)/gameengine/blphys/$(LIBNAME) + +include nan_compile.mk + +CCFLAGS += $(LEVEL_1_CPP_WARNINGS) + +CPPFLAGS += -I$(OPENGL_HEADERS) +CPPFLAGS += -I$(NAN_STRING)/include +CPPFLAGS += -I$(NAN_PYTHON)/include/python$(NAN_PYTHON_VERSION) + +CPPFLAGS += -I$(NAN_FUZZICS)/include -I$(NAN_SUMO)/include -I$(NAN_MOTO)/include +CPPFLAGS += -I$(NAN_ODE)/include +CPPFLAGS += -I$(NAN_GUARDEDALLOC)/include +CPPFLAGS += -I../../Physics/common +CPPFLAGS += -I../../Physics/Dummy +# nlin: fix this, should put in NAN_ODE dir +#CPPFLAGS += -I./ode/ode/include diff --git a/source/gameengine/Physics/BlOde/OdePhysicsController.cpp b/source/gameengine/Physics/BlOde/OdePhysicsController.cpp new file mode 100644 index 00000000000..5efd0994311 --- /dev/null +++ b/source/gameengine/Physics/BlOde/OdePhysicsController.cpp @@ -0,0 +1,625 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * The contents of this file may be used under the terms of either the GNU + * General Public License Version 2 or later (the "GPL", see + * http://www.gnu.org/licenses/gpl.html ), or the Blender License 1.0 or + * later (the "BL", see http://www.blender.org/BL/ ) which has to be + * bought from the Blender Foundation to become active, in which case the + * above mentioned GPL option does not apply. + * + * The Original Code is Copyright (C) 2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ + +#define USE_ODE +#ifdef USE_ODE + +#include "OdePhysicsController.h" +#include "PHY_IMotionState.h" + +#include <ode/ode.h> + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +/////////////////////////////////////////////////////////////////////////// +// +// general to-do list for ODE physics. This is maintained in doxygen format. +// +/// \todo determine assignment time for bounding spheres. +/// +/// it appears you have to select "sphere" for bounding volume AND "draw bounds" +/// in order for a bounding sphere to be generated. otherwise a box is generated. +/// determine exactly when and how the bounding volumes are generated and make +/// this consistent. +/// } +/// +/// \todo bounding sphere size incorrect +/// +/// it appears NOT to use the size of the shown bounding sphere (button "draw bounds"). +/// it appears instead to use the size of the "size" dynamic parameter in the +/// gamebuttons but this "size" draws an incorrectly-sized circle on screen for the +/// bounding sphere (leftover skewed size calculation from sumo?) so figure out WHERE +/// its getting the radius from. +/// +/// \todo ODE collisions must fire collision actuator +/// +/// See OdePhysicsEnvironment::OdeNearCallback. If a sensor was created to check +/// for the presence of this collision, then in the NearCallback you need to +/// take appropriate action regarding the sensor - something like checking its +/// controller and if needed firing its actuator. Need to find similar code in +/// Fuzzics which fires collision controllers/actuators. +/// +/// \todo Are ghost collisions possible? +/// +/// How do ghost collisions work? Do they require collision detection through ODE +/// and NON-CREATION of contact-joint in OdeNearCallback? Currently OdeNearCallback +/// creates joints ALWAYS for collisions. +/// +/// \todo Why is KX_GameObject::addLinearVelocity commented out? +/// +/// Try putting this code back in. +/// +/// \todo Too many non-dynamic actors bogs down ODE physics +/// +/// Lots of "geoms" (ODE static geometry) probably slows down ode. Try a test file +/// with lots of static geometry - the game performance in Blender says it is +/// spending all its time in physics, and I bet all that time is in collision +/// detection. It's ode's non-hierarchical collision detection. +/// try making a separate ode test program (not within blender) with 1000 geoms and +/// see how fast it is. if it is really slow, there is the culprit. +/// isnt someone working on an improved ODE collision detector? check +/// ode mailing list. +/// +/// +/// \todo support collision of dynas with non-dynamic triangle meshes +/// +/// ODE has trimesh-collision support but only for trimeshes without a transform +/// matrix. update ODE tricollider to support a transform matrix. this will allow +/// moving trimeshes non-dynamically (e.g. through Ipos). then collide trimeshes +/// with dynas. this allows dynamic primitives (spheres, boxes) to collide with +/// non-dynamic or kinematically controlled tri-meshes. full dynamic trimesh to +/// dynamic trimesh support is hard because it requires (a) collision and penetration +/// depth for trimesh to trimesh and (hard to compute) (b) an intertia tensor +/// (easy to compute). +/// +/// a triangle mesh collision geometry should be created when the blender +/// bounding volume (F9, EDITBUTTONS) is set to "polyheder", since this is +/// currently the place where sphere/box selection is made +/// +/// \todo specify ODE ERP+CFM in blender interface +/// +/// when ODE physics selected, have to be able to set global cfm and erp. +/// per-joint erp/cfm could be handled in constraint window. +/// +/// \todo moving infinite mass objects should impart extra impulse to objects they collide with +/// +/// currently ODE's ERP pushes them apart but doesn't account for their motion. +/// you have to detect if one body in a collision is a non-dyna. This +/// requires adding a new accessor method to +/// KX_IPhysicsInterfaceController to access the hidden m_isDyna variable, +/// currently it can only be written, not read). If one of the bodies in a +/// collision is a non-dyna, then impart an extra impulse based on the +/// motion of the static object (using its last 2 frames as an approximation +/// of its linear and angular velocity). Linear velocity is easy to +/// approximate, but angular? you have orientation at this frame and +/// orientation at previous frame. The question is what is the angular +/// velocity which would have taken you from the previous frame's orientation +/// to this frame's orientation? +/// +/// \todo allow tweaking bounding volume size +/// +/// the scene converter currently uses the blender bounding volume of the selected +/// object as the geometry for ODE collision purposes. this is good and automatic +/// intuitive - lets you choose between cube, sphere, mesh. but you need to be able +/// to tweak this size for physics. +/// +/// \todo off center meshes totally wrong for ode +/// +/// ode uses x, y, z extents regradless of center. then places geom at center of object. +/// but visual geom is not necessarily at center. need to detect off-center situations. +/// then do what? treat it as an encapsulated off-center mass, or recenter it? +/// +/// i.o.w. recalculate center, or recalculate mass distribution (using encapsulation)? +/// +/// \todo allow off-center mass +/// +/// using ode geometry encapsulators +/// +/// \todo allow entering compound geoms for complex collision shapes specified as a union of simpler shapes +/// +/// The collision shape for arbitrary triangle meshes can probably in general be +///well approximated by a compound ODE geometry object, which is merely a combination +///of many primitives (capsule, sphere, box). I eventually want to add the ability +///to associate compound geometry objects with Blender gameobjects. I think one +///way of doing this would be to add a new button in the GameButtons, "RigidBodyCompound". +///If the object is "Dynamic" + "RigidBody", then the object's bounding volume (sphere, +///box) is created. If an object is "Dynamic" + "RigidBodyCompound", then the object itself +///will merely create a "wrapper" compound object, with the actual geometry objects +///being created from the object's children in Blender. E.g. if I wanted to make a +///compound collision object consisting of a sphere and 2 boxes, I would create a +///parent gameobject with the actual triangle mesh, and set its GameButtons to +///"RigidBodyCompound". I would then create 3 children of this object, 1 sphere and +///2 boxes, and set the GameButtons for the children to be "RigidBody". Then at +///scene conversion time, the scene converter sees "RigidBodyCompound" for the +///top-level object, then appropriately traverses the children and creates the compound +///collision geometry consisting of 2 boxes and a sphere. In this way, arbitrary +///mesh-mesh collision becomes much less necessary - the artist can (or must, +///depending on your point of view!) approximate the collision shape for arbitrary +///meshes with a combination of one or more primitive shapes. I think using the +///parent/child relationship in Blender and a new button "RigidBodyCompound" for the +///parent object of a compound is a feasible way of doing this in Blender. +/// +///See ODE demo test_boxstack and look at the code when you drop a compound object +///with the "X" key. +/// +/// \todo add visual specification of constraints +/// +/// extend the armature constraint system. by using empties and constraining one empty +/// to "copy location" of another, you can get a p2p constraint between the two empties. +/// by making the two empties each a parent of a blender object, you effectively have +/// a p2p constraint between 2 blender bodies. the scene converter can detect these +/// empties, detect the constraint, and generate an ODE constraint. +/// +/// then add a new constraint type "hinge" and "slider" to correspond to ODE joints. +/// e.g. a slider would be a constraint which restricts the axis of its object to lie +/// along the same line as another axis of a different object. e.g. you constrain x-axis +/// of one empty to lie along the same line as the z-axis of another empty; this gives +/// a slider joint. +/// +/// open questions: how to handle powered joints? to what extent should/must constraints +/// be enforced during modeling? use CCD-style algorithm in modeler to enforce constraints? +/// how about ODE powered constraints e.g. motors? +/// +/// \todo enable suspension of bodies +/// ODE offers native support for suspending dynas. but what about suspending non-dynas +/// (e.g. geoms)? suspending geoms is also necessary to ease the load of ODE's (simple?) +/// collision detector. suspending dynas and geoms is important for the activity culling, +/// which apparently works at a simple level. perhaps suspension should actually +/// remove or insert geoms/dynas into the ODE space/world? is this operation (insertion/ +/// removal) fast enough at run-time? test it. if fast enough, then suspension=remove from +/// ODE simulation, awakening=insertion into ODE simulation. +/// +/// \todo python interface for tweaking constraints via python +/// +/// \todo raytesting to support gameengine sensors that need it +/// +/// \todo investigate compatibility issues with old Blender 2.25 physics engine (sumo/fuzzics) +/// is it possible to have compatibility? how hard is it? how important is it? + + +ODEPhysicsController::ODEPhysicsController(bool dyna, bool fullRigidBody, + bool phantom, class PHY_IMotionState* motionstate, struct dxSpace* space, + struct dxWorld* world, float mass,float friction,float restitution, + bool implicitsphere,float center[3],float extents[3],float radius) + : + m_OdeDyna(dyna), + m_firstTime(true), + m_bFullRigidBody(fullRigidBody), + m_bPhantom(phantom), + m_bKinematic(false), + m_bPrevKinematic(false), + m_MotionState(motionstate), + m_OdeSuspendDynamics(false), + m_space(space), + m_world(world), + m_mass(mass), + m_friction(friction), + m_restitution(restitution), + m_bodyId(0), + m_geomId(0), + m_implicitsphere(implicitsphere), + m_radius(radius) +{ + m_center[0] = center[0]; + m_center[1] = center[1]; + m_center[2] = center[2]; + m_extends[0] = extents[0]; + m_extends[1] = extents[1]; + m_extends[2] = extents[2]; +}; + + +ODEPhysicsController::~ODEPhysicsController() +{ + if (m_geomId) + { + dGeomDestroy (m_geomId); + } +} + +float ODEPhysicsController::getMass() +{ + dMass mass; + dBodyGetMass(m_bodyId,&mass); + return mass.mass; +} + +////////////////////////////////////////////////////////////////////// +/// \todo Impart some extra impulse to dynamic objects when they collide with kinematically controlled "static" objects (ODE geoms), by using last 2 frames as 1st order approximation to the linear/angular velocity, and computing an appropriate impulse. Sumo (old physics engine) did this, see for details. +/// \todo handle scaling of static ODE geoms or fail with error message if Ipo tries to change scale of a static geom object + +bool ODEPhysicsController::SynchronizeMotionStates(float time) +{ + /** + 'Late binding' of the rigidbody, because the World Scaling is not available until the scenegraph is traversed + */ + + + if (m_firstTime) + { + m_firstTime=false; + + m_MotionState->calculateWorldTransformations(); + + dQuaternion worldquat; + float worldpos[3]; + +#ifdef dDOUBLE + m_MotionState->getWorldOrientation((float)worldquat[1], + (float)worldquat[2],(float)worldquat[3],(float)worldquat[0]); +#else + m_MotionState->getWorldOrientation(worldquat[1], + worldquat[2],worldquat[3],worldquat[0]); +#endif + m_MotionState->getWorldPosition(worldpos[0],worldpos[1],worldpos[2]); + + float scaling[3]; + m_MotionState->getWorldScaling(scaling[0],scaling[1],scaling[2]); + + if (!m_bPhantom) + { + if (m_implicitsphere) + { + m_geomId = dCreateSphere (m_space,m_radius*scaling[0]); + } else + { + m_geomId = dCreateBox (m_space, m_extends[0]*scaling[0],m_extends[1]*scaling[1],m_extends[2]*scaling[2]); + } + } else + { + m_geomId=0; + } + + if (m_geomId) + dGeomSetData(m_geomId,this); + + if (!this->m_OdeDyna) + { + if (!m_bPhantom) + { + dGeomSetPosition (this->m_geomId,worldpos[0],worldpos[1],worldpos[2]); + dMatrix3 R; + dQtoR (worldquat, R); + dGeomSetRotation (this->m_geomId,R); + } + } else + { + //it's dynamic, so create a 'model' + m_bodyId = dBodyCreate(this->m_world); + dBodySetPosition (m_bodyId,worldpos[0],worldpos[1],worldpos[2]); + dBodySetQuaternion (this->m_bodyId,worldquat); + //this contains both scalar mass and inertia tensor + dMass m; + float length=1,width=1,height=1; + dMassSetBox (&m,1,m_extends[0]*scaling[0],m_extends[1]*scaling[1],m_extends[2]*scaling[2]); + dMassAdjust (&m,this->m_mass); + dBodySetMass (m_bodyId,&m); + + if (!m_bPhantom) + { + dGeomSetBody (m_geomId,m_bodyId); + } + + + } + + if (this->m_OdeDyna && !m_bFullRigidBody) + { + // ?? huh? what to do here? + } + } + + + + if (m_OdeDyna) + { + if (this->m_OdeSuspendDynamics) + { + return false; + } + + const float* worldPos = (float *)dBodyGetPosition(m_bodyId); + m_MotionState->setWorldPosition(worldPos[0],worldPos[1],worldPos[2]); + + const float* worldquat = (float *)dBodyGetQuaternion(m_bodyId); + m_MotionState->setWorldOrientation(worldquat[1],worldquat[2],worldquat[3],worldquat[0]); + } + else { + // not a dyna, so dynamics (i.e. this controller) has not updated + // anything. BUT! an Ipo or something else might have changed the + // position/orientation of this geometry. + // so update the static geom position + + /// \todo impart some extra impulse to colliding objects! + dQuaternion worldquat; + float worldpos[3]; + +#ifdef dDOUBLE + m_MotionState->getWorldOrientation((float)worldquat[1], + (float)worldquat[2],(float)worldquat[3],(float)worldquat[0]); +#else + m_MotionState->getWorldOrientation(worldquat[1], + worldquat[2],worldquat[3],worldquat[0]); +#endif + m_MotionState->getWorldPosition(worldpos[0],worldpos[1],worldpos[2]); + + float scaling[3]; + m_MotionState->getWorldScaling(scaling[0],scaling[1],scaling[2]); + + /// \todo handle scaling! what if Ipo changes scale of object? + // Must propagate to geom... is scaling geoms possible with ODE? Also + // what about scaling trimeshes, that is certainly difficult... + dGeomSetPosition (this->m_geomId,worldpos[0],worldpos[1],worldpos[2]); + dMatrix3 R; + dQtoR (worldquat, R); + dGeomSetRotation (this->m_geomId,R); + } + + return false; //it update the worldpos +} + +PHY_IMotionState* ODEPhysicsController::GetMotionState() +{ + return m_MotionState; +} + + +// kinematic methods +void ODEPhysicsController::RelativeTranslate(float dlocX,float dlocY,float dlocZ,bool local) +{ + +} +void ODEPhysicsController::RelativeRotate(const float drot[9],bool local) +{ +} +void ODEPhysicsController::setOrientation(float quatImag0,float quatImag1,float quatImag2,float quatReal) +{ + + dQuaternion worldquat; + worldquat[0] = quatReal; + worldquat[1] = quatImag0; + worldquat[2] = quatImag1; + worldquat[3] = quatImag2; + + if (!this->m_OdeDyna) + { + dMatrix3 R; + dQtoR (worldquat, R); + dGeomSetRotation (this->m_geomId,R); + } else + { + dBodySetQuaternion (m_bodyId,worldquat); + this->m_MotionState->setWorldOrientation(quatImag0,quatImag1,quatImag2,quatReal); + } + +} + +void ODEPhysicsController::getOrientation(float &quatImag0,float &quatImag1,float &quatImag2,float &quatReal) +{ + float q[4]; + this->m_MotionState->getWorldOrientation(q[0],q[1],q[2],q[3]); + quatImag0=q[0]; + quatImag1=q[1]; + quatImag2=q[2]; + quatReal=q[3]; +} + +void ODEPhysicsController::getPosition(PHY__Vector3& pos) const +{ + m_MotionState->getWorldPosition(pos[0],pos[1],pos[2]); + +} + +void ODEPhysicsController::setPosition(float posX,float posY,float posZ) +{ + if (!m_bPhantom) + { + if (!this->m_OdeDyna) + { + dGeomSetPosition (m_geomId, posX, posY, posZ); + } else + { + dBodySetPosition (m_bodyId, posX, posY, posZ); + } + } +} +void ODEPhysicsController::setScaling(float scaleX,float scaleY,float scaleZ) +{ +} + +// physics methods +void ODEPhysicsController::ApplyTorque(float torqueX,float torqueY,float torqueZ,bool local) +{ + if (m_OdeDyna) { + if(local) { + dBodyAddRelTorque(m_bodyId, torqueX, torqueY, torqueZ); + } else { + dBodyAddTorque (m_bodyId, torqueX, torqueY, torqueZ); + } + } +} + +void ODEPhysicsController::ApplyForce(float forceX,float forceY,float forceZ,bool local) +{ + if (m_OdeDyna) { + if(local) { + dBodyAddRelForce(m_bodyId, forceX, forceY, forceZ); + } else { + dBodyAddForce (m_bodyId, forceX, forceY, forceZ); + } + } +} + +void ODEPhysicsController::SetAngularVelocity(float ang_velX,float ang_velY,float ang_velZ,bool local) +{ + if (m_OdeDyna) { + if(local) { + // TODO: translate angular vel into local frame, then apply + } else { + dBodySetAngularVel (m_bodyId, ang_velX,ang_velY,ang_velZ); + } + } +} + +void ODEPhysicsController::SetLinearVelocity(float lin_velX,float lin_velY,float lin_velZ,bool local) +{ + if (m_OdeDyna) + { + dVector3 vel = {lin_velX,lin_velY,lin_velZ, 1.0}; + if (local) + { + dMatrix3 worldmat; + dVector3 localvel; + dQuaternion worldquat; + +#ifdef dDOUBLE + m_MotionState->getWorldOrientation((float)worldquat[1], + (float)worldquat[2], (float)worldquat[3],(float)worldquat[0]); +#else + m_MotionState->getWorldOrientation(worldquat[1],worldquat[2], + worldquat[3],worldquat[0]); +#endif + dQtoR (worldquat, worldmat); + + dMULTIPLY0_331 (localvel,worldmat,vel); + dBodySetLinearVel (m_bodyId, localvel[0],localvel[1],localvel[2]); + + } else + { + dBodySetLinearVel (m_bodyId, lin_velX,lin_velY,lin_velZ); + } + } +} + +void ODEPhysicsController::applyImpulse(float attachX,float attachY,float attachZ, float impulseX,float impulseY,float impulseZ) +{ + if (m_OdeDyna) + { + //apply linear and angular effect + const dReal* linvel = dBodyGetLinearVel(m_bodyId); + float mass = getMass(); + if (mass >= 0.00001f) + { + float massinv = 1.f/mass; + float newvel[3]; + newvel[0]=linvel[0]+impulseX*massinv; + newvel[1]=linvel[1]+impulseY*massinv; + newvel[2]=linvel[2]+impulseZ*massinv; + dBodySetLinearVel(m_bodyId,newvel[0],newvel[1],newvel[2]); + + const float* worldPos = (float *)dBodyGetPosition(m_bodyId); + + const float* angvelc = (float *)dBodyGetAngularVel(m_bodyId); + float angvel[3]; + angvel[0]=angvelc[0]; + angvel[1]=angvelc[1]; + angvel[2]=angvelc[2]; + + dVector3 impulse; + impulse[0]=impulseX; + impulse[1]=impulseY; + impulse[2]=impulseZ; + + dVector3 ap; + ap[0]=attachX-worldPos[0]; + ap[1]=attachY-worldPos[1]; + ap[2]=attachZ-worldPos[2]; + + dCROSS(angvel,+=,ap,impulse); + dBodySetAngularVel(m_bodyId,angvel[0],angvel[1],angvel[2]); + + } + + } + +} + +void ODEPhysicsController::SuspendDynamics() +{ + +} + +void ODEPhysicsController::RestoreDynamics() +{ + +} + + +/** + reading out information from physics +*/ +void ODEPhysicsController::GetLinearVelocity(float& linvX,float& linvY,float& linvZ) +{ + if (m_OdeDyna) + { + const float* vel = (float *)dBodyGetLinearVel(m_bodyId); + linvX = vel[0]; + linvY = vel[1]; + linvZ = vel[2]; + } else + { + linvX = 0.f; + linvY = 0.f; + linvZ = 0.f; + + } +} +/** + GetVelocity parameters are in geometric coordinates (Origin is not center of mass!). +*/ +void ODEPhysicsController::GetVelocity(const float posX,const float posY,const float posZ,float& linvX,float& linvY,float& linvZ) +{ + +} + + +void ODEPhysicsController::getReactionForce(float& forceX,float& forceY,float& forceZ) +{ + +} +void ODEPhysicsController::setRigidBody(bool rigid) +{ + +} + + +void ODEPhysicsController::PostProcessReplica(class PHY_IMotionState* motionstate,class PHY_IPhysicsController* parentctrl) +{ + m_MotionState = motionstate; + m_bKinematic = false; + m_bPrevKinematic = false; + m_firstTime = true; +} + + +void ODEPhysicsController::SetSimulatedTime(float time) +{ +} + + +void ODEPhysicsController::WriteMotionStateToDynamics(bool nondynaonly) +{ + +} +#endif diff --git a/source/gameengine/Physics/BlOde/OdePhysicsController.h b/source/gameengine/Physics/BlOde/OdePhysicsController.h new file mode 100644 index 00000000000..544d11da2ca --- /dev/null +++ b/source/gameengine/Physics/BlOde/OdePhysicsController.h @@ -0,0 +1,164 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * The contents of this file may be used under the terms of either the GNU + * General Public License Version 2 or later (the "GPL", see + * http://www.gnu.org/licenses/gpl.html ), or the Blender License 1.0 or + * later (the "BL", see http://www.blender.org/BL/ ) which has to be + * bought from the Blender Foundation to become active, in which case the + * above mentioned GPL option does not apply. + * + * The Original Code is Copyright (C) 2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef __ODE_PHYSICSCONTROLLER_H +#define __ODE_PHYSICSCONTROLLER_H + + +#include "PHY_IPhysicsController.h" + +/** + ODE Physics Controller, a special kind of a PhysicsController. + A Physics Controller is a special kind of Scene Graph Transformation Controller. + Each time the scene graph get's updated, the controller get's a chance + in the 'Update' method to reflect changes. +*/ + +class ODEPhysicsController : public PHY_IPhysicsController + +{ + + bool m_OdeDyna; + +public: + ODEPhysicsController( + bool dyna, + bool fullRigidBody, + bool phantom, + class PHY_IMotionState* motionstate, + struct dxSpace* space, + struct dxWorld* world, + float mass, + float friction, + float restitution, + bool implicitsphere, + float center[3], + float extends[3], + float radius); + + virtual ~ODEPhysicsController(); + + // kinematic methods + virtual void RelativeTranslate(float dlocX,float dlocY,float dlocZ,bool local); + virtual void RelativeRotate(const float drot[9],bool local); + virtual void getOrientation(float &quatImag0,float &quatImag1,float &quatImag2,float &quatReal); + virtual void setOrientation(float quatImag0,float quatImag1,float quatImag2,float quatReal); + virtual void setPosition(float posX,float posY,float posZ); + virtual void getPosition(PHY__Vector3& pos) const; + + virtual void setScaling(float scaleX,float scaleY,float scaleZ); + + // physics methods + virtual void ApplyTorque(float torqueX,float torqueY,float torqueZ,bool local); + virtual void ApplyForce(float forceX,float forceY,float forceZ,bool local); + virtual void SetAngularVelocity(float ang_velX,float ang_velY,float ang_velZ,bool local); + virtual void SetLinearVelocity(float lin_velX,float lin_velY,float lin_velZ,bool local); + virtual void applyImpulse(float attachX,float attachY,float attachZ, float impulseX,float impulseY,float impulseZ); + virtual void SetActive(bool active){}; + virtual void SuspendDynamics(); + virtual void RestoreDynamics(); + virtual void resolveCombinedVelocities(float linvelX,float linvelY,float linvelZ,float angVelX,float angVelY,float angVelZ) + { + //todo ? + } + + + /** + reading out information from physics + */ + virtual void GetLinearVelocity(float& linvX,float& linvY,float& linvZ); + /** + GetVelocity parameters are in geometric coordinates (Origin is not center of mass!). + */ + virtual void GetVelocity(const float posX,const float posY,const float posZ,float& linvX,float& linvY,float& linvZ); + virtual float getMass(); + virtual void getReactionForce(float& forceX,float& forceY,float& forceZ); + virtual void setRigidBody(bool rigid); + + + virtual void PostProcessReplica(class PHY_IMotionState* motionstate,class PHY_IPhysicsController* parentctrl); + + // \todo remove next line ! + virtual void SetSimulatedTime(float time); + + + virtual void WriteDynamicsToMotionState() {}; + virtual void WriteMotionStateToDynamics(bool nondynaonly); + virtual class PHY_IMotionState* GetMotionState(); + + /** + call from Scene Graph Node to 'update'. + */ + virtual bool SynchronizeMotionStates(float time); + + virtual void calcXform(){} + virtual void SetMargin(float margin) {} + virtual float GetMargin() const {return 0.f;} + virtual float GetRadius() const {return 0.f;} + virtual void SetRadius(float margin) {} + + // clientinfo for raycasts for example + virtual void* getNewClientInfo() { return m_clientInfo;} + virtual void setNewClientInfo(void* clientinfo) {m_clientInfo = clientinfo;}; + void* m_clientInfo; + + struct dxBody* GetOdeBodyId() { return m_bodyId; } + + float getFriction() { return m_friction;} + float getRestitution() { return m_restitution;} + + float GetLinVelocityMin() const { return 0.f; } + void SetLinVelocityMin(float val) { } + float GetLinVelocityMax() const { return 0.f; } + void SetLinVelocityMax(float val) { } + + +private: + + bool m_firstTime; + bool m_bFullRigidBody; + bool m_bPhantom; // special flag for objects that are not affected by physics 'resolver' + + // data to calculate fake velocities for kinematic objects (non-dynas) + bool m_bKinematic; + bool m_bPrevKinematic; + + + float m_lastTime; + bool m_OdeSuspendDynamics; + class PHY_IMotionState* m_MotionState; + + //Ode specific members + struct dxBody* m_bodyId; + struct dxGeom* m_geomId; + struct dxSpace* m_space; + struct dxWorld* m_world; + float m_mass; + float m_friction; + float m_restitution; + bool m_implicitsphere; + float m_center[3]; + float m_extends[3]; + float m_radius; +}; + +#endif //__ODE_PHYSICSCONTROLLER_H + diff --git a/source/gameengine/Physics/BlOde/OdePhysicsEnvironment.cpp b/source/gameengine/Physics/BlOde/OdePhysicsEnvironment.cpp new file mode 100644 index 00000000000..54e97858b7f --- /dev/null +++ b/source/gameengine/Physics/BlOde/OdePhysicsEnvironment.cpp @@ -0,0 +1,277 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * The contents of this file may be used under the terms of either the GNU + * General Public License Version 2 or later (the "GPL", see + * http://www.gnu.org/licenses/gpl.html ), or the Blender License 1.0 or + * later (the "BL", see http://www.blender.org/BL/ ) which has to be + * bought from the Blender Foundation to become active, in which case the + * above mentioned GPL option does not apply. + * + * The Original Code is Copyright (C) 2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#include "OdePhysicsEnvironment.h" +#include "PHY_IMotionState.h" +#include "OdePhysicsController.h" + +#include <ode/ode.h> +#include <../ode/src/joint.h> +#include <ode/odemath.h> + +ODEPhysicsEnvironment::ODEPhysicsEnvironment() +{ + m_OdeWorld = dWorldCreate(); + m_OdeSpace = dHashSpaceCreate(); + m_OdeContactGroup = dJointGroupCreate (0); + dWorldSetCFM (m_OdeWorld,1e-5f); + + m_JointGroup = dJointGroupCreate(0); + + setFixedTimeStep(true,1.f/60.f); +} + + + +ODEPhysicsEnvironment::~ODEPhysicsEnvironment() +{ + dJointGroupDestroy (m_OdeContactGroup); + dJointGroupDestroy (m_JointGroup); + + dSpaceDestroy (m_OdeSpace); + dWorldDestroy (m_OdeWorld); +} + + + +void ODEPhysicsEnvironment::setFixedTimeStep(bool useFixedTimeStep,float fixedTimeStep) +{ + m_useFixedTimeStep = useFixedTimeStep; + + if (useFixedTimeStep) + { + m_fixedTimeStep = fixedTimeStep; + } else + { + m_fixedTimeStep = 0.f; + } + m_currentTime = 0.f; + + //todo:implement fixed timestepping + +} +float ODEPhysicsEnvironment::getFixedTimeStep() +{ + return m_fixedTimeStep; +} + + + +bool ODEPhysicsEnvironment::proceedDeltaTime(double curTime,float timeStep1,float interval) +{ + + float deltaTime = timeStep1; + int numSteps = 1; + + if (m_useFixedTimeStep) + { + m_currentTime += timeStep1; + // equal to subSampling (might be a little smaller). + numSteps = (int)(m_currentTime / m_fixedTimeStep); + m_currentTime -= m_fixedTimeStep * (float)numSteps; + deltaTime = m_fixedTimeStep; + //todo: experiment by smoothing the remaining time over the substeps + } + + for (int i=0;i<numSteps;i++) + { + // ode collision update + dSpaceCollide (m_OdeSpace,this,&ODEPhysicsEnvironment::OdeNearCallback); + + int m_odeContacts = GetNumOdeContacts(); + + //physics integrator + resolver update + //dWorldStep (m_OdeWorld,deltaTime); + //dWorldQuickStep (m_OdeWorld,deltaTime); + //dWorldID w, dReal stepsize) + + //clear collision points + this->ClearOdeContactGroup(); + } + return true; +} + +void ODEPhysicsEnvironment::setGravity(float x,float y,float z) +{ + dWorldSetGravity (m_OdeWorld,x,y,z); +} + + + +int ODEPhysicsEnvironment::createConstraint(class PHY_IPhysicsController* ctrl,class PHY_IPhysicsController* ctrl2,PHY_ConstraintType type, + float pivotX,float pivotY,float pivotZ,float axisX,float axisY,float axisZ) +{ + + int constraintid = 0; + ODEPhysicsController* dynactrl = (ODEPhysicsController*)ctrl; + ODEPhysicsController* dynactrl2 = (ODEPhysicsController*)ctrl2; + + switch (type) + { + case PHY_POINT2POINT_CONSTRAINT: + { + if (dynactrl) + { + dJointID jointid = dJointCreateBall (m_OdeWorld,m_JointGroup); + struct dxBody* bodyid1 = dynactrl->GetOdeBodyId(); + struct dxBody* bodyid2=0; + const dReal* pos = dBodyGetPosition(bodyid1); + const dReal* R = dBodyGetRotation(bodyid1); + dReal offset[3] = {pivotX,pivotY,pivotZ}; + dReal newoffset[3]; + dMULTIPLY0_331 (newoffset,R,offset); + newoffset[0] += pos[0]; + newoffset[1] += pos[1]; + newoffset[2] += pos[2]; + + + if (dynactrl2) + bodyid2 = dynactrl2->GetOdeBodyId(); + + dJointAttach (jointid, bodyid1, bodyid2); + + dJointSetBallAnchor (jointid, newoffset[0], newoffset[1], newoffset[2]); + + constraintid = (int) jointid; + } + break; + } + case PHY_LINEHINGE_CONSTRAINT: + { + if (dynactrl) + { + dJointID jointid = dJointCreateHinge (m_OdeWorld,m_JointGroup); + struct dxBody* bodyid1 = dynactrl->GetOdeBodyId(); + struct dxBody* bodyid2=0; + const dReal* pos = dBodyGetPosition(bodyid1); + const dReal* R = dBodyGetRotation(bodyid1); + dReal offset[3] = {pivotX,pivotY,pivotZ}; + dReal axisset[3] = {axisX,axisY,axisZ}; + + dReal newoffset[3]; + dReal newaxis[3]; + dMULTIPLY0_331 (newaxis,R,axisset); + + dMULTIPLY0_331 (newoffset,R,offset); + newoffset[0] += pos[0]; + newoffset[1] += pos[1]; + newoffset[2] += pos[2]; + + + if (dynactrl2) + bodyid2 = dynactrl2->GetOdeBodyId(); + + dJointAttach (jointid, bodyid1, bodyid2); + + dJointSetHingeAnchor (jointid, newoffset[0], newoffset[1], newoffset[2]); + dJointSetHingeAxis(jointid,newaxis[0],newaxis[1],newaxis[2]); + + constraintid = (int) jointid; + } + break; + } + default: + { + //not yet + } + } + + return constraintid; + +} + +void ODEPhysicsEnvironment::removeConstraint(void *constraintid) +{ + if (constraintid) + { + dJointDestroy((dJointID) constraintid); + } +} + +PHY_IPhysicsController* ODEPhysicsEnvironment::rayTest(PHY_IRayCastFilterCallback &filterCallback,float fromX,float fromY,float fromZ, float toX,float toY,float toZ) +{ + + //m_OdeWorld + //collision detection / raytesting + return NULL; +} + + +void ODEPhysicsEnvironment::OdeNearCallback (void *data, dGeomID o1, dGeomID o2) +{ + // \todo if this is a registered collision sensor + // fire the callback + + int i; + // if (o1->body && o2->body) return; + ODEPhysicsEnvironment* env = (ODEPhysicsEnvironment*) data; + dBodyID b1,b2; + + b1 = dGeomGetBody(o1); + b2 = dGeomGetBody(o2); + // exit without doing anything if the two bodies are connected by a joint + if (b1 && b2 && dAreConnected (b1,b2)) return; + + ODEPhysicsController * ctrl1 =(ODEPhysicsController *)dGeomGetData(o1); + ODEPhysicsController * ctrl2 =(ODEPhysicsController *)dGeomGetData(o2); + float friction=ctrl1->getFriction(); + float restitution = ctrl1->getRestitution(); + //for friction, take minimum + + friction=(friction < ctrl2->getFriction() ? + friction :ctrl2->getFriction()); + + //restitution:take minimum + restitution = restitution < ctrl2->getRestitution()? + restitution : ctrl2->getRestitution(); + + dContact contact[3]; // up to 3 contacts per box + for (i=0; i<3; i++) { + contact[i].surface.mode = dContactBounce; //dContactMu2; + contact[i].surface.mu = friction;//dInfinity; + contact[i].surface.mu2 = 0; + contact[i].surface.bounce = restitution;//0.5; + contact[i].surface.bounce_vel = 0.1f; + contact[i].surface.slip1=0.0; + } + + if (int numc = dCollide (o1,o2,3,&contact[0].geom,sizeof(dContact))) { + // dMatrix3 RI; + // dRSetIdentity (RI); + // const dReal ss[3] = {0.02,0.02,0.02}; + for (i=0; i<numc; i++) { + dJointID c = dJointCreateContact (env->m_OdeWorld,env->m_OdeContactGroup,contact+i); + dJointAttach (c,b1,b2); + } + } +} + + +void ODEPhysicsEnvironment::ClearOdeContactGroup() +{ + dJointGroupEmpty (m_OdeContactGroup); +} + +int ODEPhysicsEnvironment::GetNumOdeContacts() +{ + return m_OdeContactGroup->num; +} + diff --git a/source/gameengine/Physics/BlOde/OdePhysicsEnvironment.h b/source/gameengine/Physics/BlOde/OdePhysicsEnvironment.h new file mode 100644 index 00000000000..54e4f7f90e1 --- /dev/null +++ b/source/gameengine/Physics/BlOde/OdePhysicsEnvironment.h @@ -0,0 +1,94 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * The contents of this file may be used under the terms of either the GNU + * General Public License Version 2 or later (the "GPL", see + * http://www.gnu.org/licenses/gpl.html ), or the Blender License 1.0 or + * later (the "BL", see http://www.blender.org/BL/ ) which has to be + * bought from the Blender Foundation to become active, in which case the + * above mentioned GPL option does not apply. + * + * The Original Code is Copyright (C) 2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef _ODEPHYSICSENVIRONMENT +#define _ODEPHYSICSENVIRONMENT + + +#include "PHY_IPhysicsEnvironment.h" + +/** +* Physics Environment takes care of stepping the simulation and is a container for physics entities (rigidbodies,constraints, materials etc.) +* A derived class may be able to 'construct' entities by loading and/or converting +*/ +class ODEPhysicsEnvironment : public PHY_IPhysicsEnvironment +{ + + bool m_useFixedTimeStep; + float m_fixedTimeStep; + float m_currentTime; + +public: + ODEPhysicsEnvironment(); + virtual ~ODEPhysicsEnvironment(); + virtual void beginFrame() {} + virtual void endFrame() {} + + +// Perform an integration step of duration 'timeStep'. + virtual bool proceedDeltaTime(double curTime,float timeStep,float interval); + virtual void setFixedTimeStep(bool useFixedTimeStep,float fixedTimeStep); + virtual float getFixedTimeStep(); + + virtual void setGravity(float x,float y,float z); + virtual int createConstraint(class PHY_IPhysicsController* ctrl,class PHY_IPhysicsController* ctrl2,PHY_ConstraintType type, + float pivotX,float pivotY,float pivotZ, + float axisX,float axisY,float axisZ); + + virtual void removeConstraint(void * constraintid); + virtual PHY_IPhysicsController* rayTest(PHY_IRayCastFilterCallback &filterCallback,float fromX,float fromY,float fromZ, float toX,float toY,float toZ); + virtual bool cullingTest(PHY_CullingCallback callback, void* userData, PHY__Vector4* planes, int nplanes, int occlusionRes) { return false; } + + + //gamelogic callbacks + virtual void addSensor(PHY_IPhysicsController* ctrl) {} + virtual void removeSensor(PHY_IPhysicsController* ctrl) {} + virtual void addTouchCallback(int response_class, PHY_ResponseCallback callback, void *user) + { + } + virtual bool requestCollisionCallback(PHY_IPhysicsController* ctrl) {return false;} + virtual bool removeCollisionCallback(PHY_IPhysicsController* ctrl) {return false;} + virtual PHY_IPhysicsController* CreateSphereController(float radius,const PHY__Vector3& position) {return 0;} + virtual PHY_IPhysicsController* CreateConeController(float coneradius,float coneheight) { return 0;} + + + + struct dxWorld* GetOdeWorld() { return m_OdeWorld; }; + struct dxSpace* GetOdeSpace() { return m_OdeSpace;}; + +private: + + + // ODE physics response + struct dxWorld* m_OdeWorld; + // ODE collision detection + struct dxSpace* m_OdeSpace; + void ClearOdeContactGroup(); + struct dxJointGroup* m_OdeContactGroup; + struct dxJointGroup* m_JointGroup; + + static void OdeNearCallback(void *data, struct dxGeom* o1, struct dxGeom* o2); + int GetNumOdeContacts(); + +}; + +#endif //_ODEPHYSICSENVIRONMENT + diff --git a/source/gameengine/Physics/BlOde/SConscript b/source/gameengine/Physics/BlOde/SConscript new file mode 100644 index 00000000000..90e949d2d86 --- /dev/null +++ b/source/gameengine/Physics/BlOde/SConscript @@ -0,0 +1,15 @@ +#!/usr/bin/python +Import ('user_options_dict') +Import ('library_env') + +phy_ode_env = library_env.Copy () + +source_files = ['OdePhysicsController.cpp', + 'OdePhysicsEnvironment.cpp'] + +phy_ode_env.Append (CPPPATH=['.', + '../common', + ]) +phy_ode_env.Append (CPPPATH=user_options_dict['ODE_INCLUDE']) + +phy_ode_env.Library (target='#'+user_options_dict['BUILD_DIR']+'/lib/PHY_Ode', source=source_files) diff --git a/source/gameengine/Physics/Dummy/Makefile b/source/gameengine/Physics/Dummy/Makefile index c016a0bebcb..b0c1b855322 100644 --- a/source/gameengine/Physics/Dummy/Makefile +++ b/source/gameengine/Physics/Dummy/Makefile @@ -39,7 +39,7 @@ CPPFLAGS += -I$(OPENGL_HEADERS) CPPFLAGS += -I$(NAN_STRING)/include CPPFLAGS += -I$(NAN_PYTHON)/include/python$(NAN_PYTHON_VERSION) -CPPFLAGS += -I$(NAN_FUZZICS)/include -I$(NAN_MOTO)/include +CPPFLAGS += -I$(NAN_FUZZICS)/include -I$(NAN_SUMO)/include -I$(NAN_MOTO)/include CPPFLAGS += -I$(NAN_GUARDEDALLOC)/include CPPFLAGS += -I../../Physics/common CPPFLAGS += -I../../Physics/Dummy diff --git a/source/gameengine/Physics/Makefile b/source/gameengine/Physics/Makefile index da0d4cafd2e..b192e497f35 100644 --- a/source/gameengine/Physics/Makefile +++ b/source/gameengine/Physics/Makefile @@ -32,6 +32,7 @@ include nan_definitions.mk SOURCEDIR = source/gameengine/Physics DIR = $(OCGDIR)/gameengine/blphys -DIRS = common Dummy Bullet +DIRS = common Sumo Dummy Bullet +#DIRS += BlOde include nan_subdirs.mk diff --git a/source/gameengine/Physics/Sumo/CMakeLists.txt b/source/gameengine/Physics/Sumo/CMakeLists.txt new file mode 100644 index 00000000000..c57a4af6706 --- /dev/null +++ b/source/gameengine/Physics/Sumo/CMakeLists.txt @@ -0,0 +1,46 @@ +# $Id$ +# ***** BEGIN GPL LICENSE BLOCK ***** +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software Foundation, +# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# The Original Code is Copyright (C) 2006, Blender Foundation +# All rights reserved. +# +# The Original Code is: all of this file. +# +# Contributor(s): Jacques Beaurain. +# +# ***** END GPL LICENSE BLOCK ***** + +SET(SRC + SumoPHYCallbackBridge.cpp + SumoPhysicsController.cpp + SumoPhysicsEnvironment.cpp + Fuzzics/src/SM_FhObject.cpp + Fuzzics/src/SM_Object.cpp + Fuzzics/src/SM_Scene.cpp + Fuzzics/src/SM_MotionState.cpp +) + +SET(INC + . + ../common + Fuzzics/include + ../../../../intern/moto/include + ../../../../extern/solid +) + +BLENDERLIB(bf_sumo "${SRC}" "${INC}") +#env.BlenderLib ( 'bf_sumo', sources, incs, [], libtype=['game2','player'], priority=[30, 70] , compileflags=cflags) diff --git a/source/gameengine/Physics/Sumo/Fuzzics/Makefile b/source/gameengine/Physics/Sumo/Fuzzics/Makefile new file mode 100644 index 00000000000..5ed2c31a1d0 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/Makefile @@ -0,0 +1,34 @@ +# +# $Id$ +# +# ***** BEGIN GPL LICENSE BLOCK ***** +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software Foundation, +# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. +# All rights reserved. +# +# The Original Code is: all of this file. +# +# Contributor(s): none yet. +# +# ***** END GPL LICENSE BLOCK ***** +# +# Bounces make to subdirectories. + +SOURCEDIR = source/gameengine/Physics/Sumo/Fuzzics +DIRS = src + +include nan_subdirs.mk diff --git a/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Callback.h b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Callback.h new file mode 100644 index 00000000000..42b5ab48ab6 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Callback.h @@ -0,0 +1,11 @@ +#ifndef SM_CALLBACK_H +#define SM_CALLBACK_H + +class SM_Callback { +public: + virtual void do_me() = 0; + virtual ~SM_Callback() {} +}; + +#endif + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/include/SM_ClientObjectInfo.h b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_ClientObjectInfo.h new file mode 100644 index 00000000000..6749e7957ec --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_ClientObjectInfo.h @@ -0,0 +1,16 @@ +#ifndef __SM_CLIENTOBJECT_INFO_H +#define __SM_CLIENTOBJECT_INFO_H + +/** + * Client Type and Additional Info. This structure can be use instead of a bare void* pointer, for safeness, and additional info for callbacks + */ + +struct SM_ClientObjectInfo +{ + int m_type; + void* m_clientobject1; + void* m_auxilary_info; +}; + +#endif //__SM_CLIENTOBJECT_INFO_H + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Debug.h b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Debug.h new file mode 100644 index 00000000000..48d5906e53d --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Debug.h @@ -0,0 +1,26 @@ + + +#ifndef __SM_DEBUG_H__ +#define __SM_DEBUG_H__ + +/* Comment this to disable all SUMO debugging printfs */ + +#define SM_DEBUG + +#ifdef SM_DEBUG + +#include <stdio.h> + +/* Uncomment this to printf all ray casts */ +//#define SM_DEBUG_RAYCAST + +/* Uncomment this to printf collision callbacks */ +//#define SM_DEBUG_BOING + +/* Uncomment this to printf Xform matrix calculations */ +//#define SM_DEBUG_XFORM + +#endif /* SM_DEBUG */ + +#endif /* __SM_DEBUG_H__ */ + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/include/SM_FhObject.h b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_FhObject.h new file mode 100644 index 00000000000..b03612ed15e --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_FhObject.h @@ -0,0 +1,56 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef SM_FHOBJECT_H +#define SM_FHOBJECT_H + +#include "SM_Object.h" + +class SM_FhObject : public SM_Object { +public: + virtual ~SM_FhObject(); + SM_FhObject(DT_ShapeHandle rayshape, MT_Vector3 ray, SM_Object *parent_object); + + const MT_Vector3& getRay() const { return m_ray; } + MT_Point3 getSpot() const { return getPosition() + m_ray; } + const MT_Vector3& getRayDirection() const { return m_ray_direction; } + SM_Object *getParentObject() const { return m_parent_object; } + + static DT_Bool ray_hit(void *client_data, + void *object1, + void *object2, + const DT_CollData *coll_data); + +private: + MT_Vector3 m_ray; + MT_Vector3 m_ray_direction; + SM_Object *m_parent_object; +}; + +#endif + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/include/SM_MotionState.h b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_MotionState.h new file mode 100644 index 00000000000..fdc45af5225 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_MotionState.h @@ -0,0 +1,77 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef SM_MOTIONSTATE_H +#define SM_MOTIONSTATE_H + +#include "MT_Transform.h" + +class SM_MotionState { +public: + SM_MotionState() : + m_time(0.0), + m_pos(0.0, 0.0, 0.0), + m_orn(0.0, 0.0, 0.0, 1.0), + m_lin_vel(0.0, 0.0, 0.0), + m_ang_vel(0.0, 0.0, 0.0) + {} + + void setPosition(const MT_Point3& pos) { m_pos = pos; } + void setOrientation(const MT_Quaternion& orn) { m_orn = orn; } + void setLinearVelocity(const MT_Vector3& lin_vel) { m_lin_vel = lin_vel; } + void setAngularVelocity(const MT_Vector3& ang_vel) { m_ang_vel = ang_vel; } + void setTime(MT_Scalar time) { m_time = time; } + + const MT_Point3& getPosition() const { return m_pos; } + const MT_Quaternion& getOrientation() const { return m_orn; } + const MT_Vector3& getLinearVelocity() const { return m_lin_vel; } + const MT_Vector3& getAngularVelocity() const { return m_ang_vel; } + + MT_Scalar getTime() const { return m_time; } + + void integrateMidpoint(MT_Scalar timeStep, const SM_MotionState &prev_state, const MT_Vector3 &velocity, const MT_Quaternion& ang_vel); + void integrateBackward(MT_Scalar timeStep, const MT_Vector3 &velocity, const MT_Quaternion& ang_vel); + void integrateForward(MT_Scalar timeStep, const SM_MotionState &prev_state); + + void lerp(const SM_MotionState &prev, const SM_MotionState &next); + void lerp(MT_Scalar t, const SM_MotionState &other); + + virtual MT_Transform getTransform() const { + return MT_Transform(m_pos, m_orn); + } + +protected: + MT_Scalar m_time; + MT_Point3 m_pos; + MT_Quaternion m_orn; + MT_Vector3 m_lin_vel; + MT_Vector3 m_ang_vel; +}; + +#endif + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Object.h b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Object.h new file mode 100644 index 00000000000..2d748a0f251 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Object.h @@ -0,0 +1,393 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef SM_OBJECT_H +#define SM_OBJECT_H + +#include <vector> + +#include <SOLID/SOLID.h> + +#include "SM_Callback.h" +#include "SM_MotionState.h" +#include <stdio.h> + +class SM_FhObject; + +/** Properties of dynamic objects */ +struct SM_ShapeProps { + MT_Scalar m_mass; ///< Total mass + MT_Scalar m_radius; ///< Bound sphere size + MT_Vector3 m_inertia; ///< Inertia, should be a tensor some time + MT_Scalar m_lin_drag; ///< Linear drag (air, water) 0 = concrete, 1 = vacuum + MT_Scalar m_ang_drag; ///< Angular drag + MT_Scalar m_friction_scaling[3]; ///< Scaling for anisotropic friction. Component in range [0, 1] + bool m_do_anisotropic; ///< Should I do anisotropic friction? + bool m_do_fh; ///< Should the object have a linear Fh spring? + bool m_do_rot_fh; ///< Should the object have an angular Fh spring? +}; + + +/** Properties of collidable objects (non-ghost objects) */ +struct SM_MaterialProps { + MT_Scalar m_restitution; ///< restitution of energy after a collision 0 = inelastic, 1 = elastic + MT_Scalar m_friction; ///< Coulomb friction (= ratio between the normal en maximum friction force) + MT_Scalar m_fh_spring; ///< Spring constant (both linear and angular) + MT_Scalar m_fh_damping; ///< Damping factor (linear and angular) in range [0, 1] + MT_Scalar m_fh_distance; ///< The range above the surface where Fh is active. + bool m_fh_normal; ///< Should the object slide off slopes? +}; + +class SM_ClientObject +{ +public: + SM_ClientObject() {} + virtual ~SM_ClientObject() {} + + virtual bool hasCollisionCallback() = 0; +}; + +/** + * SM_Object is an internal part of the Sumo physics engine. + * + * It encapsulates an object in the physics scene, and is responsible + * for calculating the collision response of objects. + */ +class SM_Object +{ +public: + SM_Object() ; + SM_Object( + DT_ShapeHandle shape, + const SM_MaterialProps *materialProps, + const SM_ShapeProps *shapeProps, + SM_Object *dynamicParent + ); + virtual ~SM_Object(); + + bool isDynamic() const; + + /* nzc experimental. There seem to be two places where kinematics + * are evaluated: proceedKinematic (called from SM_Scene) and + * proceed() in this object. I'll just try and bunge these out for + * now. */ + + void suspend(void); + void resume(void); + + void suspendDynamics(); + + void restoreDynamics(); + + bool isGhost() const; + + void suspendMaterial(); + + void restoreMaterial(); + + SM_FhObject *getFhObject() const; + + void registerCallback(SM_Callback& callback); + + void calcXform(); + void notifyClient(); + void updateInvInertiaTensor(); + + + // Save the current state information for use in the + // velocity computation in the next frame. + + void proceedKinematic(MT_Scalar timeStep); + + void saveReactionForce(MT_Scalar timeStep) ; + + void clearForce() ; + + void clearMomentum() ; + + void setMargin(MT_Scalar margin) ; + + MT_Scalar getMargin() const ; + + const SM_MaterialProps *getMaterialProps() const ; + + const SM_ShapeProps *getShapeProps() const ; + + void setPosition(const MT_Point3& pos); + void setOrientation(const MT_Quaternion& orn); + void setScaling(const MT_Vector3& scaling); + + /** + * set an external velocity. This velocity complements + * the physics velocity. So setting it does not override the + * physics velocity. It is your responsibility to clear + * this external velocity. This velocity is not subject to + * friction or damping. + */ + void setExternalLinearVelocity(const MT_Vector3& lin_vel) ; + void addExternalLinearVelocity(const MT_Vector3& lin_vel) ; + + /** Override the physics velocity */ + void addLinearVelocity(const MT_Vector3& lin_vel); + void setLinearVelocity(const MT_Vector3& lin_vel); + + /** + * Set an external angular velocity. This velocity complemetns + * the physics angular velocity so does not override it. It is + * your responsibility to clear this velocity. This velocity + * is not subject to friction or damping. + */ + void setExternalAngularVelocity(const MT_Vector3& ang_vel) ; + void addExternalAngularVelocity(const MT_Vector3& ang_vel); + + /** Override the physics angular velocity */ + void addAngularVelocity(const MT_Vector3& ang_vel); + void setAngularVelocity(const MT_Vector3& ang_vel); + + /** Clear the external velocities */ + void clearCombinedVelocities(); + + /** + * Tell the physics system to combine the external velocity + * with the physics velocity. + */ + void resolveCombinedVelocities( + const MT_Vector3 & lin_vel, + const MT_Vector3 & ang_vel + ) ; + + + + MT_Scalar getInvMass() const; + + const MT_Vector3& getInvInertia() const ; + + const MT_Matrix3x3& getInvInertiaTensor() const; + + void applyForceField(const MT_Vector3& accel) ; + + void applyCenterForce(const MT_Vector3& force) ; + + void applyTorque(const MT_Vector3& torque) ; + + /** + * Apply an impulse to the object. The impulse will be split into + * angular and linear components. + * @param attach point to apply the impulse to (in world coordinates) + */ + void applyImpulse(const MT_Point3& attach, const MT_Vector3& impulse) ; + + /** + * Applies an impulse through the center of this object. (ie the angular + * velocity will not change. + */ + void applyCenterImpulse(const MT_Vector3& impulse); + /** + * Applies an angular impulse. + */ + void applyAngularImpulse(const MT_Vector3& impulse); + + MT_Point3 getWorldCoord(const MT_Point3& local) const; + MT_Point3 getLocalCoord(const MT_Point3& world) const; + + MT_Vector3 getVelocity(const MT_Point3& local) const; + + + const MT_Vector3& getReactionForce() const ; + + void getMatrix(double *m) const ; + + const double *getMatrix() const ; + + // Still need this??? + const MT_Transform& getScaledTransform() const; + + DT_ObjectHandle getObjectHandle() const ; + DT_ShapeHandle getShapeHandle() const ; + + SM_Object *getDynamicParent() ; + + void integrateForces(MT_Scalar timeStep); + void integrateMomentum(MT_Scalar timeSteo); + + void setRigidBody(bool is_rigid_body) ; + + bool isRigidBody() const ; + + // This is the callback for handling collisions of dynamic objects + static + DT_Bool + boing( + void *client_data, + void *object1, + void *object2, + const DT_CollData *coll_data + ); + + static + DT_Bool + fix( + void *client_data, + void *object1, + void *object2, + const DT_CollData *coll_data + ); + + + SM_ClientObject *getClientObject() { return m_client_object; } + void setClientObject(SM_ClientObject *client_object) { m_client_object = client_object; } + void setPhysicsClientObject(void* physicsClientObject) + { + m_physicsClientObject = physicsClientObject; + } + void* getPhysicsClientObject() { + return m_physicsClientObject; + } + void relax(); + + SM_MotionState &getCurrentFrame(); + SM_MotionState &getPreviousFrame(); + SM_MotionState &getNextFrame(); + + const SM_MotionState &getCurrentFrame() const; + const SM_MotionState &getPreviousFrame() const; + const SM_MotionState &getNextFrame() const; + + // Motion state functions + const MT_Point3& getPosition() const; + const MT_Quaternion& getOrientation() const; + const MT_Vector3& getLinearVelocity() const; + const MT_Vector3& getAngularVelocity() const; + + MT_Scalar getTime() const; + + void setTime(MT_Scalar time); + + void interpolate(MT_Scalar timeStep); + void endFrame(); + +private: + friend class Contact; + // Tweak parameters + static MT_Scalar ImpulseThreshold; + + // return the actual linear_velocity of this object this + // is the addition of m_combined_lin_vel and m_lin_vel. + + const + MT_Vector3 + actualLinVelocity( + ) const ; + + const + MT_Vector3 + actualAngVelocity( + ) const ; + + void dynamicCollision(const MT_Point3 &local2, + const MT_Vector3 &normal, + MT_Scalar dist, + const MT_Vector3 &rel_vel, + MT_Scalar restitution, + MT_Scalar friction_factor, + MT_Scalar invMass + ); + + typedef std::vector<SM_Callback *> T_CallbackList; + + + T_CallbackList m_callbackList; // Each object can have multiple callbacks from the client (=game engine) + SM_Object *m_dynamicParent; // Collisions between parent and children are ignored + + // as the collision callback now has only information + // on an SM_Object, there must be a way that the SM_Object client + // can identify it's clientdata after a collision + SM_ClientObject *m_client_object; + + void* m_physicsClientObject; + + DT_ShapeHandle m_shape; // Shape for collision detection + + // Material and shape properties are not owned by this class. + + const SM_MaterialProps *m_materialProps; + const SM_MaterialProps *m_materialPropsBackup; // Backup in case the object temporarily becomes a ghost. + const SM_ShapeProps *m_shapeProps; + const SM_ShapeProps *m_shapePropsBackup; // Backup in case the object's dynamics is temporarily suspended + DT_ObjectHandle m_object; // A handle to the corresponding object in SOLID. + MT_Scalar m_margin; // Offset for the object's shape (also for collision detection) + MT_Vector3 m_scaling; // Non-uniform scaling of the object's shape + + double m_ogl_matrix[16]; // An OpenGL-type 4x4 matrix + MT_Transform m_xform; // The object's local coordinate system + MT_Transform m_prev_xform; // The object's local coordinate system in the previous frame + SM_MotionState m_prev_state; // The object's motion state in the previous frame + MT_Scalar m_timeStep; // The duration of the last frame + + MT_Vector3 m_reaction_impulse; // The accumulated impulse resulting from collisions + MT_Vector3 m_reaction_force; // The reaction force derived from the reaction impulse + + MT_Vector3 m_lin_mom; // Linear momentum (linear velocity times mass) + MT_Vector3 m_ang_mom; // Angular momentum (angualr velocity times inertia) + MT_Vector3 m_force; // Force on center of mass (afffects linear momentum) + MT_Vector3 m_torque; // Torque around center of mass (affects angular momentum) + + SM_MotionState m_frames[3]; + + MT_Vector3 m_error; // Error in position:- amount object must be moved to prevent intersection with scene + + // Here are the values of externally set linear and angular + // velocity. These are updated from the outside + // (actuators and python) each frame and combined with the + // physics values. At the end of each frame (at the end of a + // call to proceed) they are set to zero. This allows the + // outside world to contribute to the velocity of an object + // but still have it react to physics. + + MT_Vector3 m_combined_lin_vel; + MT_Vector3 m_combined_ang_vel; + + // The force and torque are the accumulated forces and torques applied by the client (game logic, python). + + SM_FhObject *m_fh_object; // The ray object used for Fh + bool m_suspended; // Is this object frozen? + + // Mass properties + MT_Scalar m_inv_mass; // 1/mass + MT_Vector3 m_inv_inertia; // [1/inertia_x, 1/inertia_y, 1/inertia_z] + MT_Matrix3x3 m_inv_inertia_tensor; // Inverse Inertia Tensor + + bool m_kinematic; // Have I been displaced (translated, rotated, scaled) in this frame? + bool m_prev_kinematic; // Have I been displaced (translated, rotated, scaled) in the previous frame? + bool m_is_rigid_body; // Should friction give me a change in angular momentum? + int m_static; // temporarily static. + +}; + +#endif + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Props.h b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Props.h new file mode 100644 index 00000000000..81b4cb55b45 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Props.h @@ -0,0 +1,58 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef SM_PROPSH +#define SM_PROPSH + +#include <MT_Scalar.h> + +// Properties of dynamic objects +struct SM_ShapeProps { + MT_Scalar m_mass; // Total mass + MT_Scalar m_inertia; // Inertia, should be a tensor some time + MT_Scalar m_lin_drag; // Linear drag (air, water) 0 = concrete, 1 = vacuum + MT_Scalar m_ang_drag; // Angular drag + MT_Scalar m_friction_scaling[3]; // Scaling for anisotropic friction. Component in range [0, 1] + bool m_do_anisotropic; // Should I do anisotropic friction? + bool m_do_fh; // Should the object have a linear Fh spring? + bool m_do_rot_fh; // Should the object have an angular Fh spring? +}; + + +// Properties of collidable objects (non-ghost objects) +struct SM_MaterialProps { + MT_Scalar m_restitution; // restitution of energie after a collision 0 = inelastic, 1 = elastic + MT_Scalar m_friction; // Coulomb friction (= ratio between the normal en maximum friction force) + MT_Scalar m_fh_spring; // Spring constant (both linear and angular) + MT_Scalar m_fh_damping; // Damping factor (linear and angular) in range [0, 1] + MT_Scalar m_fh_distance; // The range above the surface where Fh is active. + bool m_fh_normal; // Should the object slide off slopes? +}; + +#endif //SM_PROPSH + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Scene.h b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Scene.h new file mode 100644 index 00000000000..3d8eef2bae0 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/include/SM_Scene.h @@ -0,0 +1,172 @@ +/** + * $Id$ + * Copyright (C) 2001 NaN Technologies B.V. + * The physics scene. + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef SM_SCENE_H +#define SM_SCENE_H + +#ifdef WIN32 +#pragma warning (disable : 4786) +#endif + +#include <vector> +#include <set> +#include <utility> //needed for pair + +#include <SOLID/SOLID.h> + +#include "MT_Vector3.h" +#include "MT_Point3.h" + +#include "SM_Object.h" + +enum +{ + FH_RESPONSE, + SENSOR_RESPONSE, /* Touch Sensors */ + CAMERA_RESPONSE, /* Visibility Culling */ + OBJECT_RESPONSE, /* Object Dynamic Geometry Response */ + STATIC_RESPONSE, /* Static Geometry Response */ + + NUM_RESPONSE +}; + +class SM_Scene { +public: + SM_Scene(); + + ~SM_Scene(); + + DT_RespTableHandle getRespTableHandle() const { + return m_respTable; + } + + const MT_Vector3& getForceField() const { + return m_forceField; + } + + MT_Vector3& getForceField() { + return m_forceField; + } + + void setForceField(const MT_Vector3& forceField) { + m_forceField = forceField; + } + + void addTouchCallback(int response_class, DT_ResponseCallback callback, void *user); + + void addSensor(SM_Object& object); + void add(SM_Object& object); + void remove(SM_Object& object); + + void notifyCollision(SM_Object *obj1, SM_Object *obj2); + + void setSecondaryRespTable(DT_RespTableHandle secondaryRespTable); + DT_RespTableHandle getSecondaryRespTable() { return m_secondaryRespTable; } + + void requestCollisionCallback(SM_Object &object); + + void beginFrame(); + void endFrame(); + + // Perform an integration step of duration 'timeStep'. + // 'subSampling' is the maximum duration of a substep, i.e., + // The maximum time interval between two collision checks. + // 'subSampling' can be used to control aliasing effects + // (fast moving objects traversing through walls and such). + bool proceed(MT_Scalar curtime, MT_Scalar ticrate); + void proceed(MT_Scalar subStep); + + /** + * Test whether any objects lie on the line defined by from and + * to. The search returns the first such bject starting at from, + * or NULL if there was none. + * @returns A reference to the object, or NULL if there was none. + * @param ignore_client Do not look for collisions with this + * object. This can be useful to avoid self-hits if + * starting from the location of an object. + * @param from The start point, in world coordinates, of the search. + * @param to The end point, in world coordinates, of the search. + * @param result A store to return the point where intersection + * took place (if there was an intersection). + * @param normal A store to return the normal of the hit object on + * the location of the intersection, if it took place. + */ + SM_Object *rayTest(void *ignore_client, + const MT_Point3& from, const MT_Point3& to, + MT_Point3& result, MT_Vector3& normal) const; + +private: + + // Clear the user set velocities. + void clearObjectCombinedVelocities(); + // This is the callback for handling collisions of dynamic objects + static + DT_Bool + boing( + void *client_data, + void *object1, + void *object2, + const DT_CollData *coll_data + ); + + /** internal type */ + typedef std::vector<SM_Object *> T_ObjectList; + + /** Handle to the scene in SOLID */ + DT_SceneHandle m_scene; + /** Following response table contains the callbacks for the dynmics */ + DT_RespTableHandle m_respTable; + DT_ResponseClass m_ResponseClass[NUM_RESPONSE]; + /** + * Following response table contains callbacks for the client (= + * game engine) */ + DT_RespTableHandle m_secondaryRespTable; // Handle + DT_ResponseClass m_secondaryResponseClass[NUM_RESPONSE]; + + /** + * Following resposne table contains callbacks for fixing the simulation + * ie making sure colliding objects do not intersect. + */ + DT_RespTableHandle m_fixRespTable; + DT_ResponseClass m_fixResponseClass[NUM_RESPONSE]; + + /** The acceleration from the force field */ + MT_Vector3 m_forceField; + + /** + * The list of objects that receive motion updates and do + * collision tests. */ + T_ObjectList m_objectList; + + unsigned int m_frames; +}; + +#endif + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/sample/Makefile b/source/gameengine/Physics/Sumo/Fuzzics/sample/Makefile new file mode 100644 index 00000000000..672dff39028 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/sample/Makefile @@ -0,0 +1,25 @@ +# +# $Id$ +# Copyright (C) 2001 NaN Technologies B.V. + +DIR = $(OCGDIR)/sumo +ALLTARGETS = $(OBJS) $(DIR)/$(DEBUG_DIR)particle $(DIR)/$(DEBUG_DIR)particle0 + +include nan_compile.mk + +CPPFLAGS = -I../../include -I../include -I$(NAN_MOTO)/include +CPPFLAGS += -I$(OPENGL_HEADERS) + +clean:: + @$(RM) $(DIR)/particle $(DIR)/particle0 + @$(RM) $(DIR)/debug/particle $(DIR)/debug/particle0 + +LDFLAGS = -L$(DIR) -L/usr/X11R6/lib +OGL_LDLIBS = -lglut -lGLU -lGL -pthread +LDLIBS = -lfuzzics -lsolid $(NAN_MOTO)/lib/libmoto.a $(OGL_LDLIBS) + +$(DIR)/$(DEBUG_DIR)particle: particle.o $(DIR)/$(DEBUG_DIR)libfuzzics.a $(DIR)/$(DEBUG_DIR)libsolid.a + $(CCC) $(CCFLAGS) $(CPPFLAGS) $(LDFLAGS) $< -o $@ $(LDLIBS) + +$(DIR)/$(DEBUG_DIR)particle0: particle0.o $(DIR)/$(DEBUG_DIR)libfuzzics.a $(DIR)/$(DEBUG_DIR)libsolid.a + $(CCC) $(CCFLAGS) $(CPPFLAGS) $(LDFLAGS) $< -o $@ $(LDLIBS) diff --git a/source/gameengine/Physics/Sumo/Fuzzics/sample/particle.cpp b/source/gameengine/Physics/Sumo/Fuzzics/sample/particle.cpp new file mode 100644 index 00000000000..d7aca326b42 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/sample/particle.cpp @@ -0,0 +1,709 @@ +//#define FAKE_IT +#define USE_COMPLEX +#define QUADS + +#include <algorithm> +#include <new> +#include <GL/glut.h> + +#include "MT_MinMax.h" +#include "MT_Point3.h" +#include "MT_Vector3.h" +#include "MT_Quaternion.h" +#include "MT_Matrix3x3.h" +#include "MT_Transform.h" + +#include "SM_Object.h" +#include "SM_FhObject.h" +#include "SM_Scene.h" + +#include <SOLID/SOLID.h> + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +const MT_Scalar bowl_curv = 0.10; +const MT_Scalar timeStep = 0.02; +const MT_Scalar ground_margin = 0.0; +const MT_Scalar sphere_radius = 0.5; + +const MT_Vector3 gravity(0, -9.8, 0); + +static MT_Scalar DISTANCE = 5; + +static MT_Scalar ele = 0, azi = 0; +static MT_Point3 eye(0, 0, DISTANCE); +static MT_Point3 center(0, 0, 0); + +inline double irnd() { return 2 * MT_random() - 1; } + +static const double SCALE_BOTTOM = 0.5; +static const double SCALE_FACTOR = 2.0; + +SM_ShapeProps g_shapeProps = { + 1.0, // mass + 1.0, // inertia + 0.1, // linear drag + 0.1, // angular drag + { 1.0, 0.0, 0.0 }, // anisotropic friction + false, // do anisotropic friction? + true, // do fh? + true // do rot fh? +}; + +SM_MaterialProps g_materialProps = { + 0.7, // restitution + 0.0, // friction + 10.0, // Fh spring constant + 1.0, // Fh damping + 0.5, // Fh distance + true // Fh leveling +}; + + +void toggleIdle(); + + +void newRandom(); + +void coordSystem() { + glDisable(GL_LIGHTING); + glBegin(GL_LINES); + glColor3f(1, 0, 0); + glVertex3d(0, 0, 0); + glVertex3d(10, 0, 0); + glColor3f(0, 1, 0); + glVertex3d(0, 0, 0); + glVertex3d(0, 10, 0); + glColor3f(0, 0, 1); + glVertex3d(0, 0, 0); + glVertex3d(0, 0, 10); + glEnd(); + glEnable(GL_LIGHTING); +} + + +void display_bbox(const MT_Point3& min, const MT_Point3& max) { + glDisable(GL_DEPTH_TEST); + glDisable(GL_LIGHTING); + glColor3f(0, 1, 1); + glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); + glBegin(GL_QUAD_STRIP); + glVertex3d(min[0], min[1], min[2]); + glVertex3d(min[0], min[1], max[2]); + glVertex3d(max[0], min[1], min[2]); + glVertex3d(max[0], min[1], max[2]); + glVertex3d(max[0], max[1], min[2]); + glVertex3d(max[0], max[1], max[2]); + glVertex3d(min[0], max[1], min[2]); + glVertex3d(min[0], max[1], max[2]); + glVertex3d(min[0], min[1], min[2]); + glVertex3d(min[0], min[1], max[2]); + glEnd(); + glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); + glEnable(GL_LIGHTING); + glEnable(GL_DEPTH_TEST); +} + + + + +class GLShape { +public: + virtual void paint(GLdouble *m) const = 0; +}; + + +class GLSphere : public GLShape { + MT_Scalar radius; +public: + GLSphere(MT_Scalar r) : radius(r) {} + + void paint(GLdouble *m) const { + glPushMatrix(); + glLoadMatrixd(m); + coordSystem(); + glutSolidSphere(radius, 20, 20); + glPopMatrix(); + } +}; + + +class GLBox : public GLShape { + MT_Vector3 extent; +public: + GLBox(MT_Scalar x, MT_Scalar y, MT_Scalar z) : + extent(x, y, z) {} + + void paint(GLdouble *m) const { + glPushMatrix(); + glLoadMatrixd(m); + coordSystem(); + glPushMatrix(); + glScaled(extent[0], extent[1], extent[2]); + glutSolidCube(1.0); + glPopMatrix(); + glPopMatrix(); + } +}; + + +class GLCone : public GLShape { + MT_Scalar bottomRadius; + MT_Scalar height; + mutable GLuint displayList; + +public: + GLCone(MT_Scalar r, MT_Scalar h) : + bottomRadius(r), + height(h), + displayList(0) {} + + void paint(GLdouble *m) const { + glPushMatrix(); + glLoadMatrixd(m); + coordSystem(); + if (displayList) glCallList(displayList); + else { + GLUquadricObj *quadObj = gluNewQuadric(); + displayList = glGenLists(1); + glNewList(displayList, GL_COMPILE_AND_EXECUTE); + glPushMatrix(); + glRotatef(-90.0, 1.0, 0.0, 0.0); + glTranslatef(0.0, 0.0, -1.0); + gluQuadricDrawStyle(quadObj, (GLenum)GLU_FILL); + gluQuadricNormals(quadObj, (GLenum)GLU_SMOOTH); + gluCylinder(quadObj, bottomRadius, 0, height, 15, 10); + glPopMatrix(); + glEndList(); + } + glPopMatrix(); + } +}; + +class GLCylinder : public GLShape { + MT_Scalar radius; + MT_Scalar height; + mutable GLuint displayList; + +public: + GLCylinder(MT_Scalar r, MT_Scalar h) : + radius(r), + height(h), + displayList(0) {} + + void paint(GLdouble *m) const { + glPushMatrix(); + glLoadMatrixd(m); + coordSystem(); + if (displayList) glCallList(displayList); + else { + GLUquadricObj *quadObj = gluNewQuadric(); + displayList = glGenLists(1); + glNewList(displayList, GL_COMPILE_AND_EXECUTE); + glPushMatrix(); + glRotatef(-90.0, 1.0, 0.0, 0.0); + glTranslatef(0.0, 0.0, -1.0); + gluQuadricDrawStyle(quadObj, (GLenum)GLU_FILL); + gluQuadricNormals(quadObj, (GLenum)GLU_SMOOTH); + gluCylinder(quadObj, radius, radius, height, 15, 10); + glPopMatrix (); + glEndList(); + } + glPopMatrix(); + } +}; + +class Object; + +class Callback : public SM_Callback { +public: + Callback(Object& object) : m_object(object) {} + + virtual void do_me(); + +private: + Object& m_object; +}; + + +class Object { +public: + Object(GLShape *gl_shape, SM_Object& object) : + m_gl_shape(gl_shape), + m_object(object), + m_callback(*this) + { + m_object.registerCallback(m_callback); + } + + ~Object() {} + + void paint() { + if (m_gl_shape) { + m_gl_shape->paint(m); + // display_bbox(m_bbox.lower(), m_bbox.upper()); + } + } + + void print_reaction_force() const { + std::cout << m_object.getReactionForce() << std::endl; + } + + MT_Vector3 getAhead() { + return MT_Vector3(&m[4]); + } + + MT_Vector3 getUp() { + return MT_Vector3(&m[8]); + } + + void clearMomentum() { + m_object.clearMomentum(); + } + + void setMargin(MT_Scalar margin) { + m_object.setMargin(margin); + } + + void setScaling(const MT_Vector3& scaling) { + m_object.setScaling(scaling); + } + + const MT_Point3& getPosition() { + return m_object.getPosition(); + } + + void setPosition(const MT_Point3& pos) { + m_object.setPosition(pos); + } + + void setOrientation(const MT_Quaternion& orn) { + m_object.setOrientation(orn); + } + + void applyCenterForce(const MT_Vector3& force) { + m_object.applyCenterForce(force); + } + + void applyTorque(const MT_Vector3& torque) { + m_object.applyTorque(torque); + } + + MT_Point3 getWorldCoord(const MT_Point3& local) const { + return m_object.getWorldCoord(local); + } + + MT_Vector3 getLinearVelocity() const { + return m_object.getLinearVelocity(); + } + + MT_Vector3 getAngularVelocity() const { + return m_object.getAngularVelocity(); + } + + void setMatrix() { + m_object.calcXform(); + m_object.getMatrix(m); + } + + const double *getMatrix() { + m_object.calcXform(); + return m_object.getMatrix(); + } + +private: + GLShape *m_gl_shape; + SM_Object& m_object; + DT_Scalar m[16]; + Callback m_callback; +}; + + + +const MT_Scalar SPACE_SIZE = 2; + +static GLSphere gl_sphere(sphere_radius); +static GLBox gl_ground(50.0, 0.0, 50.0); + + + +#ifdef USE_COMPLEX + +const int GRID_SCALE = 10; +const MT_Scalar GRID_UNIT = 25.0 / GRID_SCALE; + +DT_ShapeHandle createComplex() { + DT_ShapeHandle shape = DT_NewComplexShape(); + for (int i0 = -GRID_SCALE; i0 != GRID_SCALE; ++i0) { + for (int j0 = -GRID_SCALE; j0 != GRID_SCALE; ++j0) { + int i1 = i0 + 1; + int j1 = j0 + 1; +#ifdef QUADS + DT_Begin(); + DT_Vertex(GRID_UNIT * i0, bowl_curv * i0*i0, GRID_UNIT * j0); + DT_Vertex(GRID_UNIT * i0, bowl_curv * i0*i0, GRID_UNIT * j1); + DT_Vertex(GRID_UNIT * i1, bowl_curv * i1*i1, GRID_UNIT * j1); + DT_Vertex(GRID_UNIT * i1, bowl_curv * i1*i1, GRID_UNIT * j0); + DT_End(); +#else + DT_Begin(); + DT_Vertex(GRID_UNIT * i0, 0, GRID_UNIT * j0); + DT_Vertex(GRID_UNIT * i0, 0, GRID_UNIT * j1); + DT_Vertex(GRID_UNIT * i1, 0, GRID_UNIT * j1); + DT_End(); + + DT_Begin(); + DT_Vertex(GRID_UNIT * i0, 0, GRID_UNIT * j1); + DT_Vertex(GRID_UNIT * i1, 0, GRID_UNIT * j1); + DT_Vertex(GRID_UNIT * i1, 0, GRID_UNIT * j0); + DT_End(); +#endif + + } + } + DT_EndComplexShape(); + return shape; +} + + +static DT_ShapeHandle ground_shape = createComplex(); + +#else + +static DT_ShapeHandle ground_shape = DT_Box(50, 0, 50); + +#endif + +static SM_Object sm_ground(ground_shape, &g_materialProps, 0, 0); +static Object ground(&gl_ground, sm_ground); + +static SM_Object sm_sphere(DT_Sphere(0.0), &g_materialProps, &g_shapeProps, 0); +static Object object(&gl_sphere, sm_sphere); + + +static SM_Scene g_scene; + + +bool g_hit = false; +MT_Point3 g_spot; +MT_Vector3 g_normal; + + +void Callback::do_me() +{ + m_object.setMatrix(); + m_object.print_reaction_force(); +} + +void myinit(void) { + + GLfloat light_ambient[] = { 0.0, 0.0, 0.0, 1.0 }; + GLfloat light_diffuse[] = { 1.0, 1.0, 1.0, 1.0 }; + GLfloat light_specular[] = { 1.0, 1.0, 1.0, 1.0 }; + + /* light_position is NOT default value */ + GLfloat light_position0[] = { 1.0, 1.0, 1.0, 0.0 }; + GLfloat light_position1[] = { -1.0, -1.0, -1.0, 0.0 }; + + glLightfv(GL_LIGHT0, GL_AMBIENT, light_ambient); + glLightfv(GL_LIGHT0, GL_DIFFUSE, light_diffuse); + glLightfv(GL_LIGHT0, GL_SPECULAR, light_specular); + glLightfv(GL_LIGHT0, GL_POSITION, light_position0); + + glLightfv(GL_LIGHT1, GL_AMBIENT, light_ambient); + glLightfv(GL_LIGHT1, GL_DIFFUSE, light_diffuse); + glLightfv(GL_LIGHT1, GL_SPECULAR, light_specular); + glLightfv(GL_LIGHT1, GL_POSITION, light_position1); + + + glEnable(GL_LIGHTING); + glEnable(GL_LIGHT0); + glEnable(GL_LIGHT1); + + glShadeModel(GL_SMOOTH); + + glEnable(GL_DEPTH_TEST); + glDepthFunc(GL_LESS); + + // glEnable(GL_CULL_FACE); + // glCullFace(GL_BACK); + + ground.setPosition(MT_Point3(0, -10, 0)); + ground.setOrientation(MT_Quaternion(0, 0, 0, 1)); + ground.setMatrix(); + center.setValue(0.0, 0.0, 0.0); + sm_ground.setMargin(ground_margin); + + g_scene.setForceField(gravity); + g_scene.add(sm_ground); + + object.setMargin(sphere_radius); + + g_scene.add(sm_sphere); + + + newRandom(); +} + + +//MT_Point3 cp1, cp2; +//bool intersection; + +void display(void) { + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + + ground.paint(); + object.paint(); + + if (g_hit) { + glDisable(GL_LIGHTING); + glColor3f(1, 0, 0); + + glPointSize(5); + glBegin(GL_POINTS); + glVertex3d(g_spot[0], g_spot[1], g_spot[2]); + glEnd(); + glPointSize(1); + + glColor3f(1, 1, 0); + glBegin(GL_LINES); + glVertex3d(g_spot[0], g_spot[1], g_spot[2]); + glVertex3d(g_spot[0] + g_normal[0], + g_spot[1] + g_normal[1], + g_spot[2] + g_normal[2]); + glEnd(); + glEnable(GL_LIGHTING); + } + + + +#ifdef COLLISION + glDisable(GL_DEPTH_TEST); + glDisable(GL_LIGHTING); + glColor3f(1, 1, 0); + if (intersection) { + glPointSize(5); + glBegin(GL_POINTS); + glVertex3d(cp1[0], cp1[1], cp1[2]); + glEnd(); + glPointSize(1); + } + else { + glBegin(GL_LINES); + glVertex3d(cp1[0], cp1[1], cp1[2]); + glVertex3d(cp2[0], cp2[1], cp2[2]); + glEnd(); + } + glEnable(GL_LIGHTING); + glEnable(GL_DEPTH_TEST); +#endif + + glFlush(); + glutSwapBuffers(); +} + + + + + +void newRandom() { + object.setPosition(MT_Point3(0, 0, 0)); + object.setOrientation(MT_Quaternion::random()); + object.clearMomentum(); + object.setMatrix(); + + display(); +} + +void moveAndDisplay() { + g_scene.proceed(timeStep, 0.01); + + display(); + g_hit = false; +} + + +void turn_left() { + object.applyTorque(5.0 * object.getUp()); +} + +void turn_right() { + object.applyTorque(-5.0 * object.getUp()); +} + +void forward() { + object.applyCenterForce(10.0 * object.getAhead()); +} + +void backward() { + object.applyCenterForce(-10.0 * object.getAhead()); +} + +void jump() { + object.applyCenterForce(MT_Vector3(0.0, 200.0, 0.0)); +} + + +void toggleIdle() { + static bool idle = true; + if (idle) { + glutIdleFunc(moveAndDisplay); + idle = false; + } + else { + glutIdleFunc(NULL); + idle = true; + } +} + + +void setCamera() { + glMatrixMode(GL_PROJECTION); + glLoadIdentity(); + glFrustum(-1.0, 1.0, -1.0, 1.0, 1.0, 200.0); + MT_Scalar rele = MT_radians(ele); + MT_Scalar razi = MT_radians(azi); + eye.setValue(DISTANCE * sin(razi) * cos(rele), + DISTANCE * sin(rele), + DISTANCE * cos(razi) * cos(rele)); + gluLookAt(eye[0], eye[1], eye[2], + center[0], center[1], center[2], + 0, 1, 0); + glMatrixMode(GL_MODELVIEW); + display(); +} + +const MT_Scalar STEPSIZE = 5; + +void stepLeft() { azi -= STEPSIZE; if (azi < 0) azi += 360; setCamera(); } +void stepRight() { azi += STEPSIZE; if (azi >= 360) azi -= 360; setCamera(); } +void stepFront() { ele += STEPSIZE; if (azi >= 360) azi -= 360; setCamera(); } +void stepBack() { ele -= STEPSIZE; if (azi < 0) azi += 360; setCamera(); } +void zoomIn() { DISTANCE -= 1; setCamera(); } +void zoomOut() { DISTANCE += 1; setCamera(); } + + +void myReshape(int w, int h) { + glViewport(0, 0, w, h); + setCamera(); +} + +void myKeyboard(unsigned char key, int x, int y) +{ + switch (key) + { + case 'w': forward(); break; + case 's': backward(); break; + case 'a': turn_left(); break; + case 'd': turn_right(); break; + case 'e': jump(); break; + case 'l' : stepLeft(); break; + case 'r' : stepRight(); break; + case 'f' : stepFront(); break; + case 'b' : stepBack(); break; + case 'z' : zoomIn(); break; + case 'x' : zoomOut(); break; + case 'i' : toggleIdle(); break; + case ' ' : newRandom(); break; + default: +// std::cout << "unused key : " << key << std::endl; + break; + } +} + +void mySpecial(int key, int x, int y) +{ + switch (key) + { + case GLUT_KEY_LEFT : stepLeft(); break; + case GLUT_KEY_RIGHT : stepRight(); break; + case GLUT_KEY_UP : stepFront(); break; + case GLUT_KEY_DOWN : stepBack(); break; + case GLUT_KEY_PAGE_UP : zoomIn(); break; + case GLUT_KEY_PAGE_DOWN : zoomOut(); break; + case GLUT_KEY_HOME : toggleIdle(); break; + default: +// std::cout << "unused (special) key : " << key << std::endl; + break; + } +} + +void goodbye( void) +{ + g_scene.remove(sm_ground); + g_scene.remove(sm_sphere); + + std::cout << "goodbye ..." << std::endl; + exit(0); +} + +void menu(int choice) +{ + + static int fullScreen = 0; + static int px, py, sx, sy; + + switch(choice) { + case 1: + if (fullScreen == 1) { + glutPositionWindow(px,py); + glutReshapeWindow(sx,sy); + glutChangeToMenuEntry(1,"Full Screen",1); + fullScreen = 0; + } else { + px=glutGet((GLenum)GLUT_WINDOW_X); + py=glutGet((GLenum)GLUT_WINDOW_Y); + sx=glutGet((GLenum)GLUT_WINDOW_WIDTH); + sy=glutGet((GLenum)GLUT_WINDOW_HEIGHT); + glutFullScreen(); + glutChangeToMenuEntry(1,"Close Full Screen",1); + fullScreen = 1; + } + break; + case 2: + toggleIdle(); + break; + case 3: + goodbye(); + break; + default: + break; + } +} + +void createMenu() +{ + glutCreateMenu(menu); + glutAddMenuEntry("Full Screen", 1); + glutAddMenuEntry("Toggle Idle (Start/Stop)", 2); + glutAddMenuEntry("Quit", 3); + glutAttachMenu(GLUT_RIGHT_BUTTON); +} + +int main(int argc, char **argv) { + glutInit(&argc, argv); + glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH); + glutInitWindowPosition(0, 0); + glutInitWindowSize(500, 500); + glutCreateWindow("Physics demo"); + + myinit(); + glutKeyboardFunc(myKeyboard); + glutSpecialFunc(mySpecial); + glutReshapeFunc(myReshape); + createMenu(); + glutIdleFunc(NULL); + + glutDisplayFunc(display); + glutMainLoop(); + return 0; +} + + + + + + + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/sample/particle0.cpp b/source/gameengine/Physics/Sumo/Fuzzics/sample/particle0.cpp new file mode 100644 index 00000000000..cdf0a2d8f64 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/sample/particle0.cpp @@ -0,0 +1,695 @@ +//#define FAKE_IT +#define USE_COMPLEX +#define QUADS + +#include <algorithm> +#include <new> +#include <GL/glut.h> + +#include "MT_MinMax.h" +#include "MT_Point3.h" +#include "MT_Vector3.h" +#include "MT_Quaternion.h" +#include "MT_Matrix3x3.h" +#include "MT_Transform.h" + +#include "SM_Object.h" +#include "SM_Scene.h" + +#include "solid.h" + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +const MT_Scalar bowl_curv = 0.10; +const MT_Scalar timeStep = 0.04; +const MT_Scalar ground_margin = 0.0; +const MT_Scalar sphere_radius = 0.5; + +const MT_Vector3 gravity(0, -9.8, 0); + +static MT_Scalar DISTANCE = 5; + +static MT_Scalar ele = 0, azi = 0; +static MT_Point3 eye(0, 0, DISTANCE); +static MT_Point3 center(0, 0, 0); + +inline double irnd() { return 2 * MT_random() - 1; } + +static const double SCALE_BOTTOM = 0.5; +static const double SCALE_FACTOR = 2.0; + +SM_ShapeProps g_shapeProps = { + 1.0, // mass + 1.0, // inertia + 0.9, // linear drag + 0.9 // angular drag +}; + +SM_MaterialProps g_materialProps = { + 0.7, // restitution + 0.0, // friction + 0.0, // spring constant + 0.0 // damping +}; + + +void toggleIdle(); + + +void newRandom(); + +void coordSystem() { + glDisable(GL_LIGHTING); + glBegin(GL_LINES); + glColor3f(1, 0, 0); + glVertex3d(0, 0, 0); + glVertex3d(10, 0, 0); + glColor3f(0, 1, 0); + glVertex3d(0, 0, 0); + glVertex3d(0, 10, 0); + glColor3f(0, 0, 1); + glVertex3d(0, 0, 0); + glVertex3d(0, 0, 10); + glEnd(); + glEnable(GL_LIGHTING); +} + + +void display_bbox(const MT_Point3& min, const MT_Point3& max) { + glDisable(GL_DEPTH_TEST); + glDisable(GL_LIGHTING); + glColor3f(0, 1, 1); + glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); + glBegin(GL_QUAD_STRIP); + glVertex3d(min[0], min[1], min[2]); + glVertex3d(min[0], min[1], max[2]); + glVertex3d(max[0], min[1], min[2]); + glVertex3d(max[0], min[1], max[2]); + glVertex3d(max[0], max[1], min[2]); + glVertex3d(max[0], max[1], max[2]); + glVertex3d(min[0], max[1], min[2]); + glVertex3d(min[0], max[1], max[2]); + glVertex3d(min[0], min[1], min[2]); + glVertex3d(min[0], min[1], max[2]); + glEnd(); + glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); + glEnable(GL_LIGHTING); + glEnable(GL_DEPTH_TEST); +} + + + + +class GLShape { +public: + virtual void paint(GLdouble *m) const = 0; +}; + + +class GLSphere : public GLShape { + MT_Scalar radius; +public: + GLSphere(MT_Scalar r) : radius(r) {} + + void paint(GLdouble *m) const { + glPushMatrix(); + glLoadMatrixd(m); + coordSystem(); + glutSolidSphere(radius, 20, 20); + glPopMatrix(); + } +}; + + +class GLBox : public GLShape { + MT_Vector3 extent; +public: + GLBox(MT_Scalar x, MT_Scalar y, MT_Scalar z) : + extent(x, y, z) {} + + void paint(GLdouble *m) const { + glPushMatrix(); + glLoadMatrixd(m); + coordSystem(); + glPushMatrix(); + glScaled(extent[0], extent[1], extent[2]); + glutSolidCube(1.0); + glPopMatrix(); + glPopMatrix(); + } +}; + + +class GLCone : public GLShape { + MT_Scalar bottomRadius; + MT_Scalar height; + mutable GLuint displayList; + +public: + GLCone(MT_Scalar r, MT_Scalar h) : + bottomRadius(r), + height(h), + displayList(0) {} + + void paint(GLdouble *m) const { + glPushMatrix(); + glLoadMatrixd(m); + coordSystem(); + if (displayList) glCallList(displayList); + else { + GLUquadricObj *quadObj = gluNewQuadric(); + displayList = glGenLists(1); + glNewList(displayList, GL_COMPILE_AND_EXECUTE); + glPushMatrix(); + glRotatef(-90.0, 1.0, 0.0, 0.0); + glTranslatef(0.0, 0.0, -1.0); + gluQuadricDrawStyle(quadObj, (GLenum)GLU_FILL); + gluQuadricNormals(quadObj, (GLenum)GLU_SMOOTH); + gluCylinder(quadObj, bottomRadius, 0, height, 15, 10); + glPopMatrix(); + glEndList(); + } + glPopMatrix(); + } +}; + +class GLCylinder : public GLShape { + MT_Scalar radius; + MT_Scalar height; + mutable GLuint displayList; + +public: + GLCylinder(MT_Scalar r, MT_Scalar h) : + radius(r), + height(h), + displayList(0) {} + + void paint(GLdouble *m) const { + glPushMatrix(); + glLoadMatrixd(m); + coordSystem(); + if (displayList) glCallList(displayList); + else { + GLUquadricObj *quadObj = gluNewQuadric(); + displayList = glGenLists(1); + glNewList(displayList, GL_COMPILE_AND_EXECUTE); + glPushMatrix(); + glRotatef(-90.0, 1.0, 0.0, 0.0); + glTranslatef(0.0, 0.0, -1.0); + gluQuadricDrawStyle(quadObj, (GLenum)GLU_FILL); + gluQuadricNormals(quadObj, (GLenum)GLU_SMOOTH); + gluCylinder(quadObj, radius, radius, height, 15, 10); + glPopMatrix (); + glEndList(); + } + glPopMatrix(); + } +}; + +class Object; + +class Callback : public SM_Callback { +public: + Callback(Object& object) : m_object(object) {} + + virtual void do_me(); + +private: + Object& m_object; +}; + + +class Object { +public: + Object(GLShape *gl_shape, SM_Object& object) : + m_gl_shape(gl_shape), + m_object(object), + m_callback(*this) + { + m_object.registerCallback(m_callback); + } + + ~Object() {} + + void paint() { + m_gl_shape->paint(m); + // display_bbox(m_bbox.lower(), m_bbox.upper()); + } + + MT_Vector3 getAhead() { + return MT_Vector3(-m[8], -m[9], -m[10]); + } + + void clearMomentum() { + m_object.clearMomentum(); + } + + void setMargin(MT_Scalar margin) { + m_object.setMargin(margin); + } + + void setScaling(const MT_Vector3& scaling) { + m_object.setScaling(scaling); + } + + void setPosition(const MT_Point3& pos) { + m_object.setPosition(pos); + } + + void setOrientation(const MT_Quaternion& orn) { + m_object.setOrientation(orn); + } + + void applyCenterForce(const MT_Vector3& force) { + m_object.applyCenterForce(force); + } + + void applyTorque(const MT_Vector3& torque) { + m_object.applyTorque(torque); + } + + MT_Point3 getWorldCoord(const MT_Point3& local) const { + return m_object.getWorldCoord(local); + } + + MT_Vector3 getLinearVelocity() const { + return m_object.getLinearVelocity(); + } + + void setMatrix() { + m_object.getMatrix(m); + } + +private: + GLShape *m_gl_shape; + SM_Object& m_object; + DT_Scalar m[16]; + Callback m_callback; +}; + + +void Callback::do_me() +{ + m_object.setMatrix(); +} + + +const MT_Scalar SPACE_SIZE = 2; + +static GLSphere gl_sphere(sphere_radius); +static GLBox gl_ground(50.0, 0.0, 50.0); + + + +#ifdef USE_COMPLEX + +const int GRID_SCALE = 10; +const MT_Scalar GRID_UNIT = 25.0 / GRID_SCALE; + +DT_ShapeHandle createComplex() { + DT_ShapeHandle shape = DT_NewComplexShape(); + for (int i0 = -GRID_SCALE; i0 != GRID_SCALE; ++i0) { + for (int j0 = -GRID_SCALE; j0 != GRID_SCALE; ++j0) { + int i1 = i0 + 1; + int j1 = j0 + 1; +#ifdef QUADS + DT_Begin(); + DT_Vertex(GRID_UNIT * i0, bowl_curv * i0*i0, GRID_UNIT * j0); + DT_Vertex(GRID_UNIT * i0, bowl_curv * i0*i0, GRID_UNIT * j1); + DT_Vertex(GRID_UNIT * i1, bowl_curv * i1*i1, GRID_UNIT * j1); + DT_Vertex(GRID_UNIT * i1, bowl_curv * i1*i1, GRID_UNIT * j0); + DT_End(); +#else + DT_Begin(); + DT_Vertex(GRID_UNIT * i0, 0, GRID_UNIT * j0); + DT_Vertex(GRID_UNIT * i0, 0, GRID_UNIT * j1); + DT_Vertex(GRID_UNIT * i1, 0, GRID_UNIT * j1); + DT_End(); + + DT_Begin(); + DT_Vertex(GRID_UNIT * i0, 0, GRID_UNIT * j1); + DT_Vertex(GRID_UNIT * i1, 0, GRID_UNIT * j1); + DT_Vertex(GRID_UNIT * i1, 0, GRID_UNIT * j0); + DT_End(); +#endif + + } + } + DT_EndComplexShape(); + return shape; +} + + +static DT_ShapeHandle ground_shape = createComplex(); + +#else + +static DT_ShapeHandle ground_shape = DT_Box(50, 0, 50); + +#endif + +static SM_Object sm_ground(ground_shape, &g_materialProps, 0, 0); +static Object ground(&gl_ground, sm_ground); + +static SM_Object sm_sphere(DT_Sphere(0.0), &g_materialProps, &g_shapeProps, 0); +static Object object(&gl_sphere, sm_sphere); + + +static SM_Object sm_ray(DT_Ray(0.0, -1.0, 0.0), 0, 0, 0); + +static SM_Scene g_scene; + + +void myinit(void) { + + GLfloat light_ambient[] = { 0.0, 0.0, 0.0, 1.0 }; + GLfloat light_diffuse[] = { 1.0, 1.0, 1.0, 1.0 }; + GLfloat light_specular[] = { 1.0, 1.0, 1.0, 1.0 }; + + /* light_position is NOT default value */ + GLfloat light_position0[] = { 1.0, 1.0, 1.0, 0.0 }; + GLfloat light_position1[] = { -1.0, -1.0, -1.0, 0.0 }; + + glLightfv(GL_LIGHT0, GL_AMBIENT, light_ambient); + glLightfv(GL_LIGHT0, GL_DIFFUSE, light_diffuse); + glLightfv(GL_LIGHT0, GL_SPECULAR, light_specular); + glLightfv(GL_LIGHT0, GL_POSITION, light_position0); + + glLightfv(GL_LIGHT1, GL_AMBIENT, light_ambient); + glLightfv(GL_LIGHT1, GL_DIFFUSE, light_diffuse); + glLightfv(GL_LIGHT1, GL_SPECULAR, light_specular); + glLightfv(GL_LIGHT1, GL_POSITION, light_position1); + + + glEnable(GL_LIGHTING); + glEnable(GL_LIGHT0); + glEnable(GL_LIGHT1); + + glShadeModel(GL_SMOOTH); + + glEnable(GL_DEPTH_TEST); + glDepthFunc(GL_LESS); + + // glEnable(GL_CULL_FACE); + // glCullFace(GL_BACK); + + g_scene.setForceField(gravity); + g_scene.add(sm_ground); + sm_ground.setMargin(ground_margin); + + new(&object) Object(&gl_sphere, sm_sphere); + + + object.setMargin(sphere_radius); + + g_scene.add(sm_sphere); + + ground.setPosition(MT_Point3(0, -10, 0)); + ground.setOrientation(MT_Quaternion(0, 0, 0, 1)); + ground.setMatrix(); + center.setValue(0.0, 0.0, 0.0); + + newRandom(); +} + + +//MT_Point3 cp1, cp2; +//bool intersection; + +bool g_hit = false; +MT_Point3 g_spot; +MT_Vector3 g_normal; + + +void display(void) { + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + + ground.paint(); + object.paint(); + + if (g_hit) { + glPointSize(5); + glBegin(GL_POINTS); + glVertex3d(g_spot[0], g_spot[1], g_spot[2]); + glEnd(); + glPointSize(1); + } + + + +#ifdef COLLISION + glDisable(GL_DEPTH_TEST); + glDisable(GL_LIGHTING); + glColor3f(1, 1, 0); + if (intersection) { + glPointSize(5); + glBegin(GL_POINTS); + glVertex3d(cp1[0], cp1[1], cp1[2]); + glEnd(); + glPointSize(1); + } + else { + glBegin(GL_LINES); + glVertex3d(cp1[0], cp1[1], cp1[2]); + glVertex3d(cp2[0], cp2[1], cp2[2]); + glEnd(); + } + glEnable(GL_LIGHTING); + glEnable(GL_DEPTH_TEST); +#endif + + glFlush(); + glutSwapBuffers(); +} + + + + + +void newRandom() { + object.setPosition(MT_Point3(0, 0, 0)); + object.clearMomentum(); + object.setMatrix(); + + display(); +} + +void moveAndDisplay() { + g_scene.proceed(timeStep, 0.01); + + MT_Vector3 normal(0, 1, 0); + + MT_Point3 from = object.getWorldCoord(MT_Point3(0, 0, 0)); + MT_Point3 to = from - normal * 10.0; + + g_hit = DT_ObjectRayTest(sm_ground.getObjectHandle(), + from.getValue(), + to.getValue(), g_spot.getValue(), + g_normal.getValue()); + + // Scrap +#define DO_FH +#ifdef DO_FH + MT_Scalar dist = MT_distance(from, g_spot); + if (dist < 5.0) { + MT_Vector3 lin_vel = object.getLinearVelocity(); + MT_Scalar lin_vel_normal = lin_vel.dot(normal); + + MT_Scalar spring_extent = dist + lin_vel_normal * (timeStep * 0.5); + + MT_Scalar f_spring = (5.0 - spring_extent) * 3.0; + object.applyCenterForce(normal * f_spring); + object.applyCenterForce(-lin_vel_normal * normal); + } + +#endif + + + display(); +} + + +void turn_left() { + object.applyTorque(MT_Vector3(0.0, 10.0, 0.0)); +} + +void turn_right() { + object.applyTorque(MT_Vector3(0.0, -10.0, 0.0)); +} + +void forward() { + object.applyCenterForce(20.0 * object.getAhead()); +} + +void backward() { + object.applyCenterForce(-20.0 * object.getAhead()); +} + +void jump() { + object.applyCenterForce(MT_Vector3(0.0, 200.0, 0.0)); +} + + +void toggleIdle() { + static bool idle = true; + if (idle) { + glutIdleFunc(moveAndDisplay); + idle = false; + } + else { + glutIdleFunc(NULL); + idle = true; + } +} + + +void setCamera() { + glMatrixMode(GL_PROJECTION); + glLoadIdentity(); + glFrustum(-1.0, 1.0, -1.0, 1.0, 1.0, 200.0); + MT_Scalar rele = MT_radians(ele); + MT_Scalar razi = MT_radians(azi); + eye.setValue(DISTANCE * sin(razi) * cos(rele), + DISTANCE * sin(rele), + DISTANCE * cos(razi) * cos(rele)); + gluLookAt(eye[0], eye[1], eye[2], + center[0], center[1], center[2], + 0, 1, 0); + glMatrixMode(GL_MODELVIEW); + display(); +} + +const MT_Scalar STEPSIZE = 5; + +void stepLeft() { azi -= STEPSIZE; if (azi < 0) azi += 360; setCamera(); } +void stepRight() { azi += STEPSIZE; if (azi >= 360) azi -= 360; setCamera(); } +void stepFront() { ele += STEPSIZE; if (azi >= 360) azi -= 360; setCamera(); } +void stepBack() { ele -= STEPSIZE; if (azi < 0) azi += 360; setCamera(); } +void zoomIn() { DISTANCE -= 1; setCamera(); } +void zoomOut() { DISTANCE += 1; setCamera(); } + + +void myReshape(int w, int h) { + glViewport(0, 0, w, h); + setCamera(); +} + +void myKeyboard(unsigned char key, int x, int y) +{ + switch (key) + { + case 'w': forward(); break; + case 's': backward(); break; + case 'a': turn_left(); break; + case 'd': turn_right(); break; + case 'e': jump(); break; + case 'l' : stepLeft(); break; + case 'r' : stepRight(); break; + case 'f' : stepFront(); break; + case 'b' : stepBack(); break; + case 'z' : zoomIn(); break; + case 'x' : zoomOut(); break; + case 'i' : toggleIdle(); break; + case ' ' : newRandom(); break; + default: +// std::cout << "unused key : " << key << std::endl; + break; + } +} + +void mySpecial(int key, int x, int y) +{ + switch (key) + { + case GLUT_KEY_LEFT : stepLeft(); break; + case GLUT_KEY_RIGHT : stepRight(); break; + case GLUT_KEY_UP : stepFront(); break; + case GLUT_KEY_DOWN : stepBack(); break; + case GLUT_KEY_PAGE_UP : zoomIn(); break; + case GLUT_KEY_PAGE_DOWN : zoomOut(); break; + case GLUT_KEY_HOME : toggleIdle(); break; + default: +// std::cout << "unused (special) key : " << key << std::endl; + break; + } +} + +void goodbye( void) +{ + g_scene.remove(sm_ground); + g_scene.remove(sm_sphere); + + std::cout << "goodbye ..." << std::endl; + exit(0); +} + +void menu(int choice) +{ + + static int fullScreen = 0; + static int px, py, sx, sy; + + switch(choice) { + case 1: + if (fullScreen == 1) { + glutPositionWindow(px,py); + glutReshapeWindow(sx,sy); + glutChangeToMenuEntry(1,"Full Screen",1); + fullScreen = 0; + } else { + px=glutGet((GLenum)GLUT_WINDOW_X); + py=glutGet((GLenum)GLUT_WINDOW_Y); + sx=glutGet((GLenum)GLUT_WINDOW_WIDTH); + sy=glutGet((GLenum)GLUT_WINDOW_HEIGHT); + glutFullScreen(); + glutChangeToMenuEntry(1,"Close Full Screen",1); + fullScreen = 1; + } + break; + case 2: + toggleIdle(); + break; + case 3: + goodbye(); + break; + default: + break; + } +} + +void createMenu() +{ + glutCreateMenu(menu); + glutAddMenuEntry("Full Screen", 1); + glutAddMenuEntry("Toggle Idle (Start/Stop)", 2); + glutAddMenuEntry("Quit", 3); + glutAttachMenu(GLUT_RIGHT_BUTTON); +} + +int main(int argc, char **argv) { + glutInit(&argc, argv); + glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH); + glutInitWindowPosition(0, 0); + glutInitWindowSize(500, 500); + glutCreateWindow("Physics demo"); + + myinit(); + glutKeyboardFunc(myKeyboard); + glutSpecialFunc(mySpecial); + glutReshapeFunc(myReshape); + createMenu(); + glutIdleFunc(NULL); + + glutDisplayFunc(display); + glutMainLoop(); + return 0; +} + + + + + + + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/src/Makefile b/source/gameengine/Physics/Sumo/Fuzzics/src/Makefile new file mode 100644 index 00000000000..b2744c5496a --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/src/Makefile @@ -0,0 +1,14 @@ +# +# $Id$ +# Copyright (C) 2001 NaN Technologies B.V. + +LIBNAME = fuzzics +DIR = $(OCGDIR)/gameengine/blphys/$(LIBNAME) + +include nan_compile.mk + +CCFLAGS += $(LEVEL_1_CPP_WARNINGS) + +CPPFLAGS += -I../include -I$(NAN_MOTO)/include -I../../include +CPPFLAGS += -I$(NAN_SOLID)/include + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/src/SM_FhObject.cpp b/source/gameengine/Physics/Sumo/Fuzzics/src/SM_FhObject.cpp new file mode 100644 index 00000000000..d866cdb4922 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/src/SM_FhObject.cpp @@ -0,0 +1,180 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#include "SM_FhObject.h" +#include "MT_MinMax.h" + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +SM_FhObject::SM_FhObject(DT_ShapeHandle rayshape, MT_Vector3 ray, SM_Object *parent_object) : + SM_Object(rayshape, NULL, NULL, NULL), + m_ray(ray), + m_ray_direction(ray.normalized()), + m_parent_object(parent_object) +{ +} + +SM_FhObject::~SM_FhObject() +{ + DT_DeleteShape(getShapeHandle()); +} + +DT_Bool SM_FhObject::ray_hit(void *client_data, + void *client_object1, + void *client_object2, + const DT_CollData *coll_data) +{ + + SM_FhObject *fh_object = dynamic_cast<SM_FhObject *>((SM_Object *)client_object2); + if (!fh_object) + { + std::swap(client_object1, client_object2); + fh_object = dynamic_cast<SM_FhObject *>((SM_Object *)client_object2); + } + + SM_Object *hit_object = (SM_Object *)client_object1; + const SM_MaterialProps *matProps = hit_object->getMaterialProps(); + + if ((matProps == 0) || (matProps->m_fh_distance < MT_EPSILON)) { + return DT_CONTINUE; + } + + SM_Object *cl_object = fh_object->getParentObject(); + + assert(fh_object); + + if (hit_object == cl_object) { + // Shot myself in the foot... + return DT_CONTINUE; + } + + const SM_ShapeProps *shapeProps = cl_object->getShapeProps(); + + // Exit if the client object is not dynamic. + if (shapeProps == 0) { + return DT_CONTINUE; + } + + MT_Point3 lspot; + MT_Vector3 normal; + + DT_Vector3 from, to, dnormal; + DT_Scalar dlspot; + fh_object->getPosition().getValue(from); + fh_object->getSpot().getValue(to); + + + if (DT_ObjectRayCast(hit_object->getObjectHandle(), + from, + to, + 1., + &dlspot, + dnormal)) { + + lspot = fh_object->getPosition() + (fh_object->getSpot() - fh_object->getPosition()) * dlspot; + const MT_Vector3& ray_dir = fh_object->getRayDirection(); + MT_Scalar dist = MT_distance(fh_object->getPosition(), lspot) - + cl_object->getMargin() - shapeProps->m_radius; + + normal = MT_Vector3(dnormal).safe_normalized(); + + if (dist < matProps->m_fh_distance) { + + if (shapeProps->m_do_fh) { + lspot -= hit_object->getPosition(); + MT_Vector3 rel_vel = cl_object->getLinearVelocity() - hit_object->getVelocity(lspot); + MT_Scalar rel_vel_ray = ray_dir.dot(rel_vel); + MT_Scalar spring_extent = 1.0 - dist / matProps->m_fh_distance; + + MT_Scalar i_spring = spring_extent * matProps->m_fh_spring; + MT_Scalar i_damp = rel_vel_ray * matProps->m_fh_damping; + + cl_object->addLinearVelocity(-(i_spring + i_damp) * ray_dir); + if (matProps->m_fh_normal) { + cl_object->addLinearVelocity( + (i_spring + i_damp) * + (normal - normal.dot(ray_dir) * ray_dir)); + } + + MT_Vector3 lateral = rel_vel - rel_vel_ray * ray_dir; + const SM_ShapeProps *shapeProps = cl_object->getShapeProps(); + + if (shapeProps->m_do_anisotropic) { + MT_Matrix3x3 lcs(cl_object->getOrientation()); + MT_Vector3 loc_lateral = lateral * lcs; + const MT_Vector3& friction_scaling = + shapeProps->m_friction_scaling; + + loc_lateral.scale(friction_scaling[0], + friction_scaling[1], + friction_scaling[2]); + lateral = lcs * loc_lateral; + } + + + MT_Scalar rel_vel_lateral = lateral.length(); + + if (rel_vel_lateral > MT_EPSILON) { + MT_Scalar friction_factor = matProps->m_friction; + MT_Scalar max_friction = friction_factor * MT_max(MT_Scalar(0.0), i_spring); + + MT_Scalar rel_mom_lateral = rel_vel_lateral / + cl_object->getInvMass(); + + MT_Vector3 friction = + (rel_mom_lateral > max_friction) ? + -lateral * (max_friction / rel_vel_lateral) : + -lateral; + + cl_object->applyCenterImpulse(friction); + } + } + + if (shapeProps->m_do_rot_fh) { + const double *ogl_mat = cl_object->getMatrix(); + MT_Vector3 up(&ogl_mat[8]); + MT_Vector3 t_spring = up.cross(normal) * matProps->m_fh_spring; + MT_Vector3 ang_vel = cl_object->getAngularVelocity(); + + // only rotations that tilt relative to the normal are damped + ang_vel -= ang_vel.dot(normal) * normal; + + MT_Vector3 t_damp = ang_vel * matProps->m_fh_damping; + + cl_object->addAngularVelocity(t_spring - t_damp); + } + } + } + + return DT_CONTINUE; +} + + + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/src/SM_MotionState.cpp b/source/gameengine/Physics/Sumo/Fuzzics/src/SM_MotionState.cpp new file mode 100644 index 00000000000..b8f4e0c591c --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/src/SM_MotionState.cpp @@ -0,0 +1,100 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#include <MT_Scalar.h> +#include <MT_Vector3.h> +#include <MT_Quaternion.h> + +#include "SM_MotionState.h" + +void SM_MotionState::integrateMidpoint(MT_Scalar timeStep, const SM_MotionState &prev_state, const MT_Vector3 &velocity, const MT_Quaternion& ang_vel) +{ + m_pos += (prev_state.getLinearVelocity() + velocity) * (timeStep * 0.5); + m_orn += (prev_state.getAngularVelocity() * prev_state.getOrientation() + ang_vel * m_orn) * (timeStep * 0.25); + m_orn.normalize(); +} + +void SM_MotionState::integrateBackward(MT_Scalar timeStep, const MT_Vector3 &velocity, const MT_Quaternion& ang_vel) +{ + m_pos += velocity * timeStep; + m_orn += ang_vel * m_orn * (timeStep * 0.5); + m_orn.normalize(); +} + +void SM_MotionState::integrateForward(MT_Scalar timeStep, const SM_MotionState &prev_state) +{ + m_pos += prev_state.getLinearVelocity() * timeStep; + m_orn += prev_state.getAngularVelocity() * m_orn * (timeStep * 0.5); + m_orn.normalize(); +} + +/* +// Newtonian lerp: interpolate based on Newtonian motion +void SM_MotionState::nlerp(const SM_MotionState &prev, const SM_MotionState &next) +{ + MT_Scalar dt = next.getTime() - prev.getTime(); + MT_Scalar t = getTime() - prev.getTime(); + MT_Vector3 dx = next.getPosition() - prev.getPosition(); + MT_Vector3 a = dx/(dt*dt) - prev.getLinearVelocity()/dt; + + m_pos = prev.getPosition() + prev.getLinearVelocity()*t + a*t*t; +} +*/ + +void SM_MotionState::lerp(const SM_MotionState &prev, const SM_MotionState &next) +{ + MT_Scalar dt = next.getTime() - prev.getTime(); + if (MT_fuzzyZero(dt)) + { + *this = next; + return; + } + + MT_Scalar x = (getTime() - prev.getTime())/dt; + + m_pos = x*next.getPosition() + (1-x)*prev.getPosition(); + + m_orn = prev.getOrientation().slerp(next.getOrientation(), 1-x); + + m_lin_vel = x*next.getLinearVelocity() + (1-x)*prev.getLinearVelocity(); + m_ang_vel = x*next.getAngularVelocity() + (1-x)*prev.getAngularVelocity(); +} + +void SM_MotionState::lerp(MT_Scalar t, const SM_MotionState &other) +{ + MT_Scalar x = (t - getTime())/(other.getTime() - getTime()); + m_pos = (1-x)*m_pos + x*other.getPosition(); + + m_orn = other.getOrientation().slerp(m_orn, x); + + m_lin_vel = (1-x)*m_lin_vel + x*other.getLinearVelocity(); + m_ang_vel = (1-x)*m_ang_vel + x*other.getAngularVelocity(); + + m_time = t; +} + diff --git a/source/gameengine/Physics/Sumo/Fuzzics/src/SM_Object.cpp b/source/gameengine/Physics/Sumo/Fuzzics/src/SM_Object.cpp new file mode 100644 index 00000000000..4b2c7cae008 --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/src/SM_Object.cpp @@ -0,0 +1,1298 @@ +/** + * $Id$ + * Copyright (C) 2001 NaN Technologies B.V. + * The basic physics object. + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +#ifdef WIN32 +// This warning tells us about truncation of __long__ stl-generated names. +// It can occasionally cause DevStudio to have internal compiler warnings. +#pragma warning( disable : 4786 ) +#endif + +#include "MT_assert.h" + +#include "SM_Object.h" +#include "SM_Scene.h" +#include "SM_FhObject.h" +#include "SM_Debug.h" + +#include "MT_MinMax.h" + +MT_Scalar SM_Object::ImpulseThreshold = -1.0; + +struct Contact +{ + SM_Object *obj1; + SM_Object *obj2; + MT_Vector3 normal; + MT_Point3 pos; + + // Sort objects by height + bool operator()(const Contact *a, const Contact *b) + { + return a->pos[2] < b->pos[2]; + } + + Contact(SM_Object *o1, SM_Object *o2, const MT_Vector3 nor, const MT_Point3 p) + : obj1(o1), + obj2(o2), + normal(nor), + pos(p) + { + } + + Contact() + { + } + + void resolve() + { + if (obj1->m_static || obj2->m_static) + { + if (obj1->isDynamic()) + { + if (obj1->m_static && obj2->m_static) + { + if (obj1->m_static < obj2->m_static) + { + obj2->m_error -= normal; + obj2->m_static = obj1->m_static + 1; + } + else + { + obj1->m_error += normal; + obj1->m_static = obj2->m_static + 1; + } + } + else + { + if (obj1->m_static) + { + obj2->m_error -= normal; + obj2->m_static = obj1->m_static + 1; + } + else + { + obj1->m_error += normal; + obj1->m_static = obj2->m_static + 1; + } + } + } + else + { + obj2->m_error -= normal; + obj2->m_static = 1; + } + } + else + { + // This distinction between dynamic and non-dynamic objects should not be + // necessary. Non-dynamic objects are assumed to have infinite mass. + if (obj1->isDynamic()) { + MT_Vector3 error = normal * 0.5f; + obj1->m_error += error; + obj2->m_error -= error; + } + else { + // Same again but now obj1 is non-dynamic + obj2->m_error -= normal; + obj2->m_static = obj1->m_static + 1; + } + } + + } + + + typedef std::set<Contact*, Contact> Set; +}; + +static Contact::Set contacts; + +SM_Object::SM_Object( + DT_ShapeHandle shape, + const SM_MaterialProps *materialProps, + const SM_ShapeProps *shapeProps, + SM_Object *dynamicParent) : + + m_dynamicParent(dynamicParent), + m_client_object(0), + m_physicsClientObject(0), + m_shape(shape), + m_materialProps(materialProps), + m_materialPropsBackup(0), + m_shapeProps(shapeProps), + m_shapePropsBackup(0), + m_margin(0.0), + m_scaling(1.0, 1.0, 1.0), + m_reaction_impulse(0.0, 0.0, 0.0), + m_reaction_force(0.0, 0.0, 0.0), + m_lin_mom(0.0, 0.0, 0.0), + m_ang_mom(0.0, 0.0, 0.0), + m_force(0.0, 0.0, 0.0), + m_torque(0.0, 0.0, 0.0), + m_error(0.0, 0.0, 0.0), + m_combined_lin_vel (0.0, 0.0, 0.0), + m_combined_ang_vel (0.0, 0.0, 0.0), + m_fh_object(0), + m_inv_mass(0.0), + m_inv_inertia(0., 0., 0.), + m_kinematic(false), + m_prev_kinematic(false), + m_is_rigid_body(false), + m_static(0) +{ + m_object = DT_CreateObject(this, shape); + m_xform.setIdentity(); + m_xform.getValue(m_ogl_matrix); + if (shapeProps) + { + if (shapeProps->m_do_fh || shapeProps->m_do_rot_fh) + { + DT_Vector3 zero = {0., 0., 0.}, ray = {0.0, 0.0, -10.0}; + m_fh_object = new SM_FhObject(DT_NewLineSegment(zero, ray), MT_Vector3(ray), this); + //printf("SM_Object:: WARNING! fh disabled.\n"); + } + m_inv_mass = 1. / shapeProps->m_mass; + m_inv_inertia = MT_Vector3(1./shapeProps->m_inertia[0], 1./shapeProps->m_inertia[1], 1./shapeProps->m_inertia[2]); + } + updateInvInertiaTensor(); + m_suspended = false; +} + + + void +SM_Object:: +integrateForces( + MT_Scalar timeStep +){ + if (!m_suspended) { + m_prev_state = getNextFrame(); + m_prev_state.setLinearVelocity(actualLinVelocity()); + m_prev_state.setAngularVelocity(actualAngVelocity()); + if (isDynamic()) { + // Integrate momentum (forward Euler) + m_lin_mom += m_force * timeStep; + m_ang_mom += m_torque * timeStep; + // Drain momentum because of air/water resistance + m_lin_mom *= pow(m_shapeProps->m_lin_drag, timeStep); + m_ang_mom *= pow(m_shapeProps->m_ang_drag, timeStep); + // Set velocities according momentum + getNextFrame().setLinearVelocity(m_lin_mom * m_inv_mass); + getNextFrame().setAngularVelocity(m_inv_inertia_tensor * m_ang_mom); + } + } + +}; + + void +SM_Object:: +integrateMomentum( + MT_Scalar timeStep +){ + // Integrate position and orientation + + // only do it for objects with linear and/or angular velocity + // else clients with hierarchies may get into trouble + if (!actualLinVelocity().fuzzyZero() || !actualAngVelocity().fuzzyZero()) + { + + // those MIDPOINT and BACKWARD integration methods are + // in this form not ok with some testfiles ! + // For a release build please use forward euler unless completely tested + +//#define MIDPOINT +//#define BACKWARD +#ifdef MIDPOINT +// Midpoint rule + getNextFrame().integrateMidpoint(timeStep, m_prev_state, actualLinVelocity(), actualAngVelocity()); +#elif defined BACKWARD +// Backward Euler + getNextFrame().integrateBackward(timeStep, actualLinVelocity(), actualAngVelocity()); +#else +// Forward Euler + getNextFrame().integrateForward(timeStep, m_prev_state); +#endif + + calcXform(); + notifyClient(); + + } +} + +/** + * dynamicCollision computes the response to a collision. + * + * @param local2 the contact point in local coordinates. + * @param normal the contact normal. + * @param dist the penetration depth of the contact. (unused) + * @param rel_vel the relative velocity of the objects + * @param restitution the amount of momentum conserved in the collision. Range: 0.0 - 1.0 + * @param friction_factor the amount of friction between the two surfaces. + * @param invMass the inverse mass of the collision objects (1.0 / mass) + */ +void SM_Object::dynamicCollision(const MT_Point3 &local2, + const MT_Vector3 &normal, + MT_Scalar dist, + const MT_Vector3 &rel_vel, + MT_Scalar restitution, + MT_Scalar friction_factor, + MT_Scalar invMass +) +{ + /** + * rel_vel_normal is the relative velocity in the contact normal direction. + */ + MT_Scalar rel_vel_normal = normal.dot(rel_vel); + + /** + * if rel_vel_normal > 0, the objects are moving apart! + */ + if (rel_vel_normal < -MT_EPSILON) { + /** + * if rel_vel_normal < ImpulseThreshold, scale the restitution down. + * This should improve the simulation where the object is stacked. + */ + restitution *= MT_min(MT_Scalar(1.0), rel_vel_normal/ImpulseThreshold); + + MT_Scalar impulse = -(1.0 + restitution) * rel_vel_normal; + + if (isRigidBody()) + { + MT_Vector3 temp = getInvInertiaTensor() * local2.cross(normal); + impulse /= invMass + normal.dot(temp.cross(local2)); + + /** + * Apply impulse at the collision point. + * Take rotational inertia into account. + */ + applyImpulse(local2 + getNextFrame().getPosition(), impulse * normal); + } else { + /** + * Apply impulse through object center. (no rotation.) + */ + impulse /= invMass; + applyCenterImpulse( impulse * normal ); + } + + MT_Vector3 external = m_combined_lin_vel + m_combined_ang_vel.cross(local2); + MT_Vector3 lateral = rel_vel - external - normal * (rel_vel_normal - external.dot(normal)); +#if 0 + // test - only do friction on the physics part of the + // velocity. + vel1 -= obj1->m_combined_lin_vel; + vel2 -= obj2->m_combined_lin_vel; + + // This should look familiar.... + rel_vel = vel2 - vel1; + rel_vel_normal = normal.dot(rel_vel); +#endif + /** + * The friction part starts here!!!!!!!! + * + * Compute the lateral component of the relative velocity + * lateral actually points in the opposite direction, i.e., + * into the direction of the friction force. + */ + if (m_shapeProps->m_do_anisotropic) { + + /** + * For anisotropic friction we scale the lateral component, + * rather than compute a direction-dependent fricition + * factor. For this the lateral component is transformed to + * local coordinates. + */ + + MT_Matrix3x3 lcs(getNextFrame().getOrientation()); + + /** + * We cannot use m_xform.getBasis() for the matrix, since + * it might contain a non-uniform scaling. + * OPT: it's a bit daft to compute the matrix since the + * quaternion itself can be used to do the transformation. + */ + MT_Vector3 loc_lateral = lateral * lcs; + + /** + * lcs is orthogonal so lcs.inversed() == lcs.transposed(), + * and lcs.transposed() * lateral == lateral * lcs. + */ + const MT_Vector3& friction_scaling = + m_shapeProps->m_friction_scaling; + + // Scale the local lateral... + loc_lateral.scale(friction_scaling[0], + friction_scaling[1], + friction_scaling[2]); + // ... and transform it back to global coordinates + lateral = lcs * loc_lateral; + } + + /** + * A tiny Coulomb friction primer: + * The Coulomb friction law states that the magnitude of the + * maximum possible friction force depends linearly on the + * magnitude of the normal force. + * + * \f[ + F_max_friction = friction_factor * F_normal + \f] + * + * (NB: independent of the contact area!!) + * + * The friction factor depends on the material. + * We use impulses rather than forces but let us not be + * bothered by this. + */ + MT_Scalar rel_vel_lateral = lateral.length(); + + if (rel_vel_lateral > MT_EPSILON) { + lateral /= rel_vel_lateral; + + // Compute the maximum friction impulse + MT_Scalar max_friction = + friction_factor * MT_max(MT_Scalar(0.0), impulse); + + // I guess the GEN_max is not necessary, so let's check it + + MT_assert(impulse >= 0.0); + + /** + * Here's the trick. We compute the impulse to make the + * lateral velocity zero. (Make the objects stick together + * at the contact point. If this impulse is larger than + * the maximum possible friction impulse, then shrink its + * magnitude to the maximum friction. + */ + + if (isRigidBody()) { + + /** + * For rigid bodies we take the inertia into account, + * since the friction impulse is going to change the + * angular momentum as well. + */ + MT_Vector3 temp = getInvInertiaTensor() * local2.cross(lateral); + MT_Scalar impulse_lateral = rel_vel_lateral / + (invMass + lateral.dot(temp.cross(local2))); + + MT_Scalar friction = MT_min(impulse_lateral, max_friction); + applyImpulse(local2 + getNextFrame().getPosition(), -lateral * friction); + } + else { + MT_Scalar impulse_lateral = rel_vel_lateral / invMass; + + MT_Scalar friction = MT_min(impulse_lateral, max_friction); + applyCenterImpulse( -friction * lateral); + } + + + } + + //calcXform(); + //notifyClient(); + + } +} + +static void AddCallback(SM_Scene *scene, SM_Object *obj1, SM_Object *obj2) +{ + // If we have callbacks on either of the client objects, do a collision test + // and add a callback if they intersect. + DT_Vector3 v; + if ((obj1->getClientObject() && obj1->getClientObject()->hasCollisionCallback()) || + (obj2->getClientObject() && obj2->getClientObject()->hasCollisionCallback()) && + DT_GetIntersect(obj1->getObjectHandle(), obj2->getObjectHandle(), v)) + scene->notifyCollision(obj1, obj2); +} + +DT_Bool SM_Object::boing( + void *client_data, + void *object1, + void *object2, + const DT_CollData *coll_data +){ + SM_Scene *scene = (SM_Scene *)client_data; + SM_Object *obj1 = (SM_Object *)object1; + SM_Object *obj2 = (SM_Object *)object2; + + // at this point it is unknown whether we are really intersecting (broad phase) + + DT_Vector3 p1, p2; + if (!obj2->isDynamic()) { + std::swap(obj1, obj2); + } + + // If one of the objects is a ghost then ignore it for the dynamics + if (obj1->isGhost() || obj2->isGhost()) { + AddCallback(scene, obj1, obj2); + return DT_CONTINUE; + } + + // Objects do not collide with parent objects + if (obj1->getDynamicParent() == obj2 || obj2->getDynamicParent() == obj1) { + AddCallback(scene, obj1, obj2); + return DT_CONTINUE; + } + + if (!obj2->isDynamic()) { + AddCallback(scene, obj1, obj2); + return DT_CONTINUE; + } + + // Get collision data from SOLID + if (!DT_GetPenDepth(obj1->getObjectHandle(), obj2->getObjectHandle(), p1, p2)) + return DT_CONTINUE; + + MT_Point3 local1(p1), local2(p2); + MT_Vector3 normal(local2 - local1); + MT_Scalar dist = normal.length(); + + if (dist < MT_EPSILON) + return DT_CONTINUE; + + // Now we are definitely intersecting. + + // Set callbacks for game engine. + if ((obj1->getClientObject() && obj1->getClientObject()->hasCollisionCallback()) || + (obj2->getClientObject() && obj2->getClientObject()->hasCollisionCallback())) + scene->notifyCollision(obj1, obj2); + + local1 -= obj1->getNextFrame().getPosition(); + local2 -= obj2->getNextFrame().getPosition(); + + // Calculate collision parameters + MT_Vector3 rel_vel = obj1->getVelocity(local1) - obj2->getVelocity(local2); + + MT_Scalar restitution = + MT_min(obj1->getMaterialProps()->m_restitution, + obj2->getMaterialProps()->m_restitution); + + MT_Scalar friction_factor = + MT_min(obj1->getMaterialProps()->m_friction, + obj2->getMaterialProps()->m_friction); + + MT_Scalar invMass = obj1->getInvMass() + obj2->getInvMass(); + + normal /= dist; + + // Calculate reactions + if (obj1->isDynamic()) + obj1->dynamicCollision(local1, normal, dist, rel_vel, restitution, friction_factor, invMass); + + if (obj2->isDynamic()) + { + obj2->dynamicCollision(local2, -normal, dist, -rel_vel, restitution, friction_factor, invMass); + if (!obj1->isDynamic() || obj1->m_static) + obj2->m_static = obj1->m_static + 1; + } + + return DT_CONTINUE; +} + +DT_Bool SM_Object::fix( + void *client_data, + void *object1, + void *object2, + const DT_CollData *coll_data +){ + SM_Object *obj1 = (SM_Object *)object1; + SM_Object *obj2 = (SM_Object *)object2; + + // If one of the objects is a ghost then ignore it for the dynamics + if (obj1->isGhost() || obj2->isGhost()) { + return DT_CONTINUE; + } + + if (obj1->getDynamicParent() == obj2 || obj2->getDynamicParent() == obj1) { + return DT_CONTINUE; + } + + if (!obj2->isDynamic()) { + std::swap(obj1, obj2); + } + + if (!obj2->isDynamic()) { + return DT_CONTINUE; + } + + // obj1 points to a dynamic object + DT_Vector3 p1, p2; + if (!DT_GetPenDepth(obj1->getObjectHandle(), obj2->getObjectHandle(), p1, p2)) + return DT_CONTINUE; + MT_Point3 local1(p1), local2(p2); + // Get collision data from SOLID + MT_Vector3 normal(local2 - local1); + + MT_Scalar dist = normal.dot(normal); + if (dist < MT_EPSILON || dist > obj2->m_shapeProps->m_radius*obj2->m_shapeProps->m_radius) + return DT_CONTINUE; + + + if ((obj1->m_static || !obj1->isDynamic()) && obj1->m_static < obj2->m_static) + { + obj2->m_static = obj1->m_static + 1; + } else if (obj2->m_static && obj2->m_static < obj1->m_static) + { + obj1->m_static = obj2->m_static + 1; + } + + contacts.insert(new Contact(obj1, obj2, normal, MT_Point3(local1 + 0.5*(local2 - local1)))); + + + return DT_CONTINUE; +} + +void SM_Object::relax(void) +{ + for (Contact::Set::iterator csit = contacts.begin() ; csit != contacts.end(); ++csit) + { + (*csit)->resolve(); + delete (*csit); + } + + contacts.clear(); + if (m_error.fuzzyZero()) + return; + //std::cout << "SM_Object::relax: { " << m_error << " }" << std::endl; + + getNextFrame().setPosition(getNextFrame().getPosition() + m_error); + m_error.setValue(0., 0., 0.); + //calcXform(); + //notifyClient(); +} + +SM_Object::SM_Object() : + m_dynamicParent(0), + m_client_object(0), + m_physicsClientObject(0), + m_shape(0), + m_materialProps(0), + m_materialPropsBackup(0), + m_shapeProps(0), + m_shapePropsBackup(0), + m_object(0), + m_margin(0.0), + m_scaling(1.0, 1.0, 1.0), + m_reaction_impulse(0.0, 0.0, 0.0), + m_reaction_force(0.0, 0.0, 0.0), + m_lin_mom(0.0, 0.0, 0.0), + m_ang_mom(0.0, 0.0, 0.0), + m_force(0.0, 0.0, 0.0), + m_torque(0.0, 0.0, 0.0), + m_error(0.0, 0.0, 0.0), + m_combined_lin_vel (0.0, 0.0, 0.0), + m_combined_ang_vel (0.0, 0.0, 0.0), + m_fh_object(0), + m_kinematic(false), + m_prev_kinematic(false), + m_is_rigid_body(false) +{ + // warning no initialization of variables done by moto. +} + +SM_Object:: +~SM_Object() { + if (m_fh_object) + delete m_fh_object; + + DT_DestroyObject(m_object); + m_object = NULL; +} + + bool +SM_Object:: +isDynamic( +) const { + return m_shapeProps != 0; +} + +/* nzc experimental. There seem to be two places where kinematics + * are evaluated: proceedKinematic (called from SM_Scene) and + * proceed() in this object. I'll just try and bunge these out for + * now. */ + void +SM_Object:: +suspend( +){ + if (!m_suspended) { + m_suspended = true; + suspendDynamics(); + } +} + + void +SM_Object:: +resume( +) { + if (m_suspended) { + m_suspended = false; + restoreDynamics(); + } +} + + void +SM_Object:: +suspendDynamics( +) { + if (m_shapeProps) { + m_shapePropsBackup = m_shapeProps; + m_shapeProps = 0; + } +} + + void +SM_Object:: +restoreDynamics( +) { + if (m_shapePropsBackup) { + m_shapeProps = m_shapePropsBackup; + m_shapePropsBackup = 0; + } +} + + bool +SM_Object:: +isGhost( +) const { + return m_materialProps == 0; +} + + void +SM_Object:: +suspendMaterial( +) { + if (m_materialProps) { + m_materialPropsBackup = m_materialProps; + m_materialProps = 0; + } +} + + void +SM_Object:: +restoreMaterial( +) { + if (m_materialPropsBackup) { + m_materialProps = m_materialPropsBackup; + m_materialPropsBackup = 0; + } +} + + SM_FhObject * +SM_Object:: +getFhObject( +) const { + return m_fh_object; +} + + void +SM_Object:: +registerCallback( + SM_Callback& callback +) { + m_callbackList.push_back(&callback); +} + +// Set the local coordinate system according to the current state + void +SM_Object:: +calcXform() { +#ifdef SM_DEBUG_XFORM + printf("SM_Object::calcXform m_pos = { %-0.5f, %-0.5f, %-0.5f }\n", + m_pos[0], m_pos[1], m_pos[2]); + printf(" m_orn = { %-0.5f, %-0.5f, %-0.5f, %-0.5f }\n", + m_orn[0], m_orn[1], m_orn[2], m_orn[3]); + printf(" m_scaling = { %-0.5f, %-0.5f, %-0.5f }\n", + m_scaling[0], m_scaling[1], m_scaling[2]); +#endif + m_xform.setOrigin(getNextFrame().getPosition()); + m_xform.setBasis(MT_Matrix3x3(getNextFrame().getOrientation(), m_scaling)); + m_xform.getValue(m_ogl_matrix); + + /* Blender has been known to crash here. + This usually means SM_Object *this has been deleted more than once. */ + DT_SetMatrixd(m_object, m_ogl_matrix); + if (m_fh_object) { + m_fh_object->setPosition(getNextFrame().getPosition()); + m_fh_object->calcXform(); + } + updateInvInertiaTensor(); +#ifdef SM_DEBUG_XFORM + printf("\n | %-0.5f %-0.5f %-0.5f %-0.5f |\n", + m_ogl_matrix[0], m_ogl_matrix[4], m_ogl_matrix[ 8], m_ogl_matrix[12]); + printf( " | %-0.5f %-0.5f %-0.5f %-0.5f |\n", + m_ogl_matrix[1], m_ogl_matrix[5], m_ogl_matrix[ 9], m_ogl_matrix[13]); + printf( "m_ogl_matrix = | %-0.5f %-0.5f %-0.5f %-0.5f |\n", + m_ogl_matrix[2], m_ogl_matrix[6], m_ogl_matrix[10], m_ogl_matrix[14]); + printf( " | %-0.5f %-0.5f %-0.5f %-0.5f |\n\n", + m_ogl_matrix[3], m_ogl_matrix[7], m_ogl_matrix[11], m_ogl_matrix[15]); +#endif +} + + void +SM_Object::updateInvInertiaTensor() +{ + m_inv_inertia_tensor = m_xform.getBasis().scaled(m_inv_inertia[0], m_inv_inertia[1], m_inv_inertia[2]) * m_xform.getBasis().transposed(); +} + +// Call callbacks to notify the client of a change of placement + void +SM_Object:: +notifyClient() { + T_CallbackList::iterator i; + for (i = m_callbackList.begin(); i != m_callbackList.end(); ++i) { + (*i)->do_me(); + } +} + + +// Save the current state information for use in the velocity computation in the next frame. + void +SM_Object:: +proceedKinematic( + MT_Scalar timeStep +) { + /* nzc: need to bunge this for the logic bubbling as well? */ + if (!m_suspended) { + m_prev_kinematic = m_kinematic; + if (m_kinematic) { + m_prev_xform = m_xform; + m_timeStep = timeStep; + calcXform(); + m_kinematic = false; + } + } +} + + void +SM_Object:: +saveReactionForce( + MT_Scalar timeStep +) { + if (isDynamic()) { + m_reaction_force = m_reaction_impulse / timeStep; + m_reaction_impulse.setValue(0.0, 0.0, 0.0); + } +} + + void +SM_Object:: +clearForce( +) { + m_force.setValue(0.0, 0.0, 0.0); + m_torque.setValue(0.0, 0.0, 0.0); +} + + void +SM_Object:: +clearMomentum( +) { + m_lin_mom.setValue(0.0, 0.0, 0.0); + m_ang_mom.setValue(0.0, 0.0, 0.0); +} + + void +SM_Object:: +setMargin( + MT_Scalar margin +) { + m_margin = margin; + DT_SetMargin(m_object, margin); +} + + MT_Scalar +SM_Object:: +getMargin( +) const { + return m_margin; +} + +const + SM_MaterialProps * +SM_Object:: +getMaterialProps( +) const { + return m_materialProps; +} + +const + SM_ShapeProps * +SM_Object:: +getShapeProps( +) const { + return m_shapeProps; +} + + void +SM_Object:: +setPosition( + const MT_Point3& pos +){ + m_kinematic = true; + getNextFrame().setPosition(pos); + endFrame(); +} + + void +SM_Object:: +setOrientation( + const MT_Quaternion& orn +){ + MT_assert(!orn.fuzzyZero()); + m_kinematic = true; + getNextFrame().setOrientation(orn); + endFrame(); +} + + void +SM_Object:: +setScaling( + const MT_Vector3& scaling +){ + m_kinematic = true; + m_scaling = scaling; +} + +/** + * Functions to handle linear velocity + */ + + void +SM_Object:: +setExternalLinearVelocity( + const MT_Vector3& lin_vel +) { + m_combined_lin_vel=lin_vel; +} + + void +SM_Object:: +addExternalLinearVelocity( + const MT_Vector3& lin_vel +) { + m_combined_lin_vel+=lin_vel; +} + + void +SM_Object:: +addLinearVelocity( + const MT_Vector3& lin_vel +){ + setLinearVelocity(getNextFrame().getLinearVelocity() + lin_vel); +} + + void +SM_Object:: +setLinearVelocity( + const MT_Vector3& lin_vel +){ + getNextFrame().setLinearVelocity(lin_vel); + if (m_shapeProps) { + m_lin_mom = getNextFrame().getLinearVelocity() * m_shapeProps->m_mass; + } +} + +/** + * Functions to handle angular velocity + */ + + void +SM_Object:: +setExternalAngularVelocity( + const MT_Vector3& ang_vel +) { + m_combined_ang_vel = ang_vel; +} + + void +SM_Object:: +addExternalAngularVelocity( + const MT_Vector3& ang_vel +) { + m_combined_ang_vel += ang_vel; +} + + void +SM_Object:: +setAngularVelocity( + const MT_Vector3& ang_vel +) { + getNextFrame().setAngularVelocity(ang_vel); + if (m_shapeProps) { + m_ang_mom = getNextFrame().getAngularVelocity() * m_shapeProps->m_inertia; + } +} + + void +SM_Object:: +addAngularVelocity( + const MT_Vector3& ang_vel +) { + setAngularVelocity(getNextFrame().getAngularVelocity() + ang_vel); +} + + + void +SM_Object:: +clearCombinedVelocities( +) { + m_combined_lin_vel = MT_Vector3(0,0,0); + m_combined_ang_vel = MT_Vector3(0,0,0); +} + + void +SM_Object:: +resolveCombinedVelocities( + const MT_Vector3 & lin_vel, + const MT_Vector3 & ang_vel +) { + + // Different behaviours for dynamic and non-dynamic + // objects. For non-dynamic we just set the velocity to + // zero. For dynmic the physics velocity has to be + // taken into account. We must make an arbitrary decision + // on how to resolve the 2 velocities. Choices are + // Add the physics velocity to the linear velocity. Objects + // will just keep on moving in the direction they were + // last set in - untill external forces affect them. + // Set the combinbed linear and physics velocity to zero. + // Set the physics velocity in the direction of the set velocity + // zero. + if (isDynamic()) { + +#if 1 + getNextFrame().setLinearVelocity(getNextFrame().getLinearVelocity() + lin_vel); + getNextFrame().setAngularVelocity(getNextFrame().getAngularVelocity() + ang_vel); +#else + + //compute the component of the physics velocity in the + // direction of the set velocity and set it to zero. + MT_Vector3 lin_vel_norm = lin_vel.normalized(); + + setLinearVelocity(getNextFrame().getLinearVelocity() - (getNextFrame().getLinearVelocity().dot(lin_vel_norm) * lin_vel_norm)); +#endif + m_lin_mom = getNextFrame().getLinearVelocity() * m_shapeProps->m_mass; + m_ang_mom = getNextFrame().getAngularVelocity() * m_shapeProps->m_inertia; + clearCombinedVelocities(); + + } + +} + + + MT_Scalar +SM_Object:: +getInvMass( +) const { + return m_inv_mass; + // OPT: cache the result of this division rather than compute it each call +} + + const MT_Vector3& +SM_Object:: +getInvInertia( +) const { + return m_inv_inertia; + // OPT: cache the result of this division rather than compute it each call +} + + const MT_Matrix3x3& +SM_Object:: +getInvInertiaTensor( +) const { + return m_inv_inertia_tensor; +} + + void +SM_Object:: +applyForceField( + const MT_Vector3& accel +) { + if (m_shapeProps) { + m_force += m_shapeProps->m_mass * accel; // F = m * a + } +} + + void +SM_Object:: +applyCenterForce( + const MT_Vector3& force +) { + m_force += force; +} + + void +SM_Object:: +applyTorque( + const MT_Vector3& torque +) { + m_torque += torque; +} + + void +SM_Object:: +applyImpulse( + const MT_Point3& attach, const MT_Vector3& impulse +) { + applyCenterImpulse(impulse); // Change in linear momentum + applyAngularImpulse((attach - getNextFrame().getPosition()).cross(impulse)); // Change in angular momentump +} + + void +SM_Object:: +applyCenterImpulse( + const MT_Vector3& impulse +) { + if (m_shapeProps) { + m_lin_mom += impulse; + m_reaction_impulse += impulse; + getNextFrame().setLinearVelocity(m_lin_mom * m_inv_mass); + + // The linear velocity is immedialtely updated since otherwise + // simultaneous collisions will get a double impulse. + } +} + + void +SM_Object:: +applyAngularImpulse( + const MT_Vector3& impulse +) { + if (m_shapeProps) { + m_ang_mom += impulse; + getNextFrame().setAngularVelocity( m_inv_inertia_tensor * m_ang_mom); + } +} + + MT_Point3 +SM_Object:: +getWorldCoord( + const MT_Point3& local +) const { + return m_xform(local); +} + + MT_Vector3 +SM_Object:: +getVelocity( + const MT_Point3& local +) const { + if (m_prev_kinematic && !isDynamic()) + { + // For displaced objects the velocity is faked using the previous state. + // Dynamic objects get their own velocity, not the faked velocity. + // (Dynamic objects shouldn't be displaced in the first place!!) + return (m_xform(local) - m_prev_xform(local)) / m_timeStep; + } + + // NB: m_xform.getBasis() * local == m_xform(local) - m_xform.getOrigin() + return actualLinVelocity() + actualAngVelocity().cross(local); +} + + +const + MT_Vector3& +SM_Object:: +getReactionForce( +) const { + return m_reaction_force; +} + + void +SM_Object:: +getMatrix( + double *m +) const { + std::copy(&m_ogl_matrix[0], &m_ogl_matrix[16], &m[0]); +} + +const + double * +SM_Object:: +getMatrix( +) const { + return m_ogl_matrix; +} + +// Still need this??? +const + MT_Transform& +SM_Object:: +getScaledTransform( +) const { + return m_xform; +} + + DT_ObjectHandle +SM_Object:: +getObjectHandle( +) const { + return m_object; +} + + DT_ShapeHandle +SM_Object:: +getShapeHandle( +) const { + return m_shape; +} + + SM_Object * +SM_Object:: +getDynamicParent( +) { + return m_dynamicParent; +} + + void +SM_Object:: +setRigidBody( + bool is_rigid_body +) { + m_is_rigid_body = is_rigid_body; +} + + bool +SM_Object:: +isRigidBody( +) const { + return m_is_rigid_body; +} + +const + MT_Vector3 +SM_Object:: +actualLinVelocity( +) const { + return m_combined_lin_vel + getNextFrame().getLinearVelocity(); +}; + +const + MT_Vector3 +SM_Object:: +actualAngVelocity( +) const { + return m_combined_ang_vel + getNextFrame().getAngularVelocity(); +} + + +SM_MotionState& +SM_Object:: +getCurrentFrame() +{ + return m_frames[1]; +} + +SM_MotionState& +SM_Object:: +getPreviousFrame() +{ + return m_frames[0]; +} + +SM_MotionState & +SM_Object:: +getNextFrame() +{ + return m_frames[2]; +} + +const SM_MotionState & +SM_Object:: +getCurrentFrame() const +{ + return m_frames[1]; +} + +const SM_MotionState & +SM_Object:: +getPreviousFrame() const +{ + return m_frames[0]; +} + +const SM_MotionState & +SM_Object:: +getNextFrame() const +{ + return m_frames[2]; +} + + +const MT_Point3& +SM_Object:: +getPosition() const +{ + return m_frames[1].getPosition(); +} + +const MT_Quaternion& +SM_Object:: +getOrientation() const +{ + return m_frames[1].getOrientation(); +} + +const MT_Vector3& +SM_Object:: +getLinearVelocity() const +{ + return m_frames[1].getLinearVelocity(); +} + +const MT_Vector3& +SM_Object:: +getAngularVelocity() const +{ + return m_frames[1].getAngularVelocity(); +} + +void +SM_Object:: +interpolate(MT_Scalar timeStep) +{ + if (!actualLinVelocity().fuzzyZero() || !actualAngVelocity().fuzzyZero()) + { + getCurrentFrame().setTime(timeStep); + getCurrentFrame().lerp(getPreviousFrame(), getNextFrame()); + notifyClient(); + } +} + +void +SM_Object:: +endFrame() +{ + getPreviousFrame() = getNextFrame(); + getCurrentFrame() = getNextFrame(); + m_static = 0; +} diff --git a/source/gameengine/Physics/Sumo/Fuzzics/src/SM_Scene.cpp b/source/gameengine/Physics/Sumo/Fuzzics/src/SM_Scene.cpp new file mode 100644 index 00000000000..f0791bbf89f --- /dev/null +++ b/source/gameengine/Physics/Sumo/Fuzzics/src/SM_Scene.cpp @@ -0,0 +1,378 @@ +/** + * $Id$ + * Copyright (C) 2001 NaN Technologies B.V. + * The physics scene. + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +#ifdef WIN32 +#pragma warning(disable : 4786) // shut off 255 char limit debug template warning +#endif + +#include "SM_Scene.h" +#include "SM_Object.h" +#include "SM_FhObject.h" + +#include "SM_Debug.h" + +#include <algorithm> + +SM_Scene::SM_Scene() : + m_scene(DT_CreateScene()), + m_respTable(DT_CreateRespTable()), + m_secondaryRespTable(DT_CreateRespTable()), + m_fixRespTable(DT_CreateRespTable()), + m_forceField(0.0, 0.0, 0.0), + m_frames(0) +{ + for (int i = 0 ; i < NUM_RESPONSE; i++) + { + m_ResponseClass[i] = DT_GenResponseClass(m_respTable); + m_secondaryResponseClass[i] = DT_GenResponseClass(m_secondaryRespTable); + m_fixResponseClass[i] = DT_GenResponseClass(m_fixRespTable); + } + + /* Sensor */ + DT_AddPairResponse(m_respTable, m_ResponseClass[SENSOR_RESPONSE], m_ResponseClass[SENSOR_RESPONSE], 0, DT_NO_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[SENSOR_RESPONSE], m_ResponseClass[STATIC_RESPONSE], SM_Scene::boing, DT_SIMPLE_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[SENSOR_RESPONSE], m_ResponseClass[OBJECT_RESPONSE], SM_Scene::boing, DT_SIMPLE_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[SENSOR_RESPONSE], m_ResponseClass[FH_RESPONSE], 0, DT_NO_RESPONSE, this); + + /* Static */ + DT_AddPairResponse(m_respTable, m_ResponseClass[STATIC_RESPONSE], m_ResponseClass[SENSOR_RESPONSE], SM_Scene::boing, DT_SIMPLE_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[STATIC_RESPONSE], m_ResponseClass[STATIC_RESPONSE], 0, DT_NO_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[STATIC_RESPONSE], m_ResponseClass[OBJECT_RESPONSE], SM_Object::boing, DT_BROAD_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[STATIC_RESPONSE], m_ResponseClass[FH_RESPONSE], SM_FhObject::ray_hit, DT_SIMPLE_RESPONSE, this); + + /* Object */ + DT_AddPairResponse(m_respTable, m_ResponseClass[OBJECT_RESPONSE], m_ResponseClass[SENSOR_RESPONSE], SM_Scene::boing, DT_SIMPLE_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[OBJECT_RESPONSE], m_ResponseClass[STATIC_RESPONSE], SM_Object::boing, DT_BROAD_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[OBJECT_RESPONSE], m_ResponseClass[OBJECT_RESPONSE], SM_Object::boing, DT_BROAD_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[OBJECT_RESPONSE], m_ResponseClass[FH_RESPONSE], SM_FhObject::ray_hit, DT_SIMPLE_RESPONSE, this); + + /* Fh Object */ + DT_AddPairResponse(m_respTable, m_ResponseClass[FH_RESPONSE], m_ResponseClass[SENSOR_RESPONSE], 0, DT_NO_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[FH_RESPONSE], m_ResponseClass[STATIC_RESPONSE], SM_FhObject::ray_hit, DT_SIMPLE_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[FH_RESPONSE], m_ResponseClass[OBJECT_RESPONSE], SM_FhObject::ray_hit, DT_SIMPLE_RESPONSE, this); + DT_AddPairResponse(m_respTable, m_ResponseClass[FH_RESPONSE], m_ResponseClass[FH_RESPONSE], 0, DT_NO_RESPONSE, this); + + /* Object (Fix Pass) */ + DT_AddPairResponse(m_fixRespTable, m_ResponseClass[OBJECT_RESPONSE], m_ResponseClass[SENSOR_RESPONSE], 0, DT_NO_RESPONSE, this); + DT_AddPairResponse(m_fixRespTable, m_ResponseClass[OBJECT_RESPONSE], m_ResponseClass[STATIC_RESPONSE], SM_Object::fix, DT_BROAD_RESPONSE, this); + DT_AddPairResponse(m_fixRespTable, m_ResponseClass[OBJECT_RESPONSE], m_ResponseClass[OBJECT_RESPONSE], SM_Object::fix, DT_BROAD_RESPONSE, this); + DT_AddPairResponse(m_fixRespTable, m_ResponseClass[OBJECT_RESPONSE], m_ResponseClass[FH_RESPONSE], 0, DT_NO_RESPONSE, this); +} + +void SM_Scene::addTouchCallback(int response_class, DT_ResponseCallback callback, void *user) +{ + DT_AddClassResponse(m_secondaryRespTable, m_secondaryResponseClass[response_class], callback, DT_BROAD_RESPONSE, user); +} + +void SM_Scene::addSensor(SM_Object& object) +{ + T_ObjectList::iterator i = + std::find(m_objectList.begin(), m_objectList.end(), &object); + if (i == m_objectList.end()) + { + object.calcXform(); + m_objectList.push_back(&object); + DT_AddObject(m_scene, object.getObjectHandle()); + DT_SetResponseClass(m_respTable, object.getObjectHandle(), m_ResponseClass[SENSOR_RESPONSE]); + DT_SetResponseClass(m_secondaryRespTable, object.getObjectHandle(), m_secondaryResponseClass [SENSOR_RESPONSE]); + DT_SetResponseClass(m_fixRespTable, object.getObjectHandle(), m_fixResponseClass[SENSOR_RESPONSE]); + } +} + +void SM_Scene::add(SM_Object& object) { + object.calcXform(); + m_objectList.push_back(&object); + DT_AddObject(m_scene, object.getObjectHandle()); + if (object.isDynamic()) { + DT_SetResponseClass(m_respTable, object.getObjectHandle(), m_ResponseClass[OBJECT_RESPONSE]); + DT_SetResponseClass(m_secondaryRespTable, object.getObjectHandle(), m_secondaryResponseClass[OBJECT_RESPONSE]); + DT_SetResponseClass(m_fixRespTable, object.getObjectHandle(), m_fixResponseClass[OBJECT_RESPONSE]); + } else { + DT_SetResponseClass(m_respTable, object.getObjectHandle(), m_ResponseClass[STATIC_RESPONSE]); + DT_SetResponseClass(m_secondaryRespTable, object.getObjectHandle(), m_secondaryResponseClass[STATIC_RESPONSE]); + DT_SetResponseClass(m_fixRespTable, object.getObjectHandle(), m_fixResponseClass[STATIC_RESPONSE]); + } + + SM_FhObject *fh_object = object.getFhObject(); + + if (fh_object) { + DT_AddObject(m_scene, fh_object->getObjectHandle()); + DT_SetResponseClass(m_respTable, fh_object->getObjectHandle(), m_ResponseClass[FH_RESPONSE]); + DT_SetResponseClass(m_secondaryRespTable, fh_object->getObjectHandle(), m_secondaryResponseClass[FH_RESPONSE]); + DT_SetResponseClass(m_fixRespTable, fh_object->getObjectHandle(), m_fixResponseClass[FH_RESPONSE]); + } +} + +void SM_Scene::requestCollisionCallback(SM_Object &object) +{ + DT_SetResponseClass(m_respTable, object.getObjectHandle(), m_ResponseClass[OBJECT_RESPONSE]); + DT_SetResponseClass(m_secondaryRespTable, object.getObjectHandle(), m_secondaryResponseClass[OBJECT_RESPONSE]); +// DT_SetResponseClass(m_fixRespTable, object.getObjectHandle(), m_fixResponseClass[OBJECT_RESPONSE]); +} + +void SM_Scene::remove(SM_Object& object) { + //std::cout << "SM_Scene::remove this =" << this << "object = " << &object << std::endl; + T_ObjectList::iterator i = + std::find(m_objectList.begin(), m_objectList.end(), &object); + if (!(i == m_objectList.end())) + { + std::swap(*i, m_objectList.back()); + m_objectList.pop_back(); + DT_RemoveObject(m_scene, object.getObjectHandle()); + + SM_FhObject *fh_object = object.getFhObject(); + + if (fh_object) { + DT_RemoveObject(m_scene, fh_object->getObjectHandle()); + } + } + else { + // tried to remove an object that is not in the scene + //assert(false); + } +} + +void SM_Scene::beginFrame() +{ + T_ObjectList::iterator i; + // Apply a forcefield (such as gravity) + for (i = m_objectList.begin(); i != m_objectList.end(); ++i) + (*i)->applyForceField(m_forceField); + +} + +void SM_Scene::endFrame() +{ + T_ObjectList::iterator i; + for (i = m_objectList.begin(); i != m_objectList.end(); ++i) + (*i)->clearForce(); +} + +bool SM_Scene::proceed(MT_Scalar curtime, MT_Scalar ticrate) +{ + if (!m_frames) + { + if (ticrate > 0.) + m_frames = (unsigned int)(curtime*ticrate) + 1.0; + else + m_frames = (unsigned int)(curtime*65536.0); + } + + // Divide the timeStep into a number of subsamples of size roughly + // equal to subS (might be a little smaller). + MT_Scalar subStep; + int num_samples; + int frames = m_frames; + + // Compute the number of steps to do this update. + if (ticrate > 0.0) + { + // Fixed time step + subStep = 1.0/ticrate; + num_samples = (unsigned int)(curtime*ticrate + 1.0) - m_frames; + + if (num_samples > 4) + { + std::cout << "Dropping physics frames! frames:" << num_samples << " substep: " << subStep << std::endl; + MT_Scalar tr = ticrate; + do + { + frames = frames / 2; + tr = tr / 2.0; + num_samples = (unsigned int)(curtime*tr + 1.0) - frames; + subStep *= 2.0; + } while (num_samples > 8); + std::cout << " frames:" << num_samples << " substep: " << subStep << std::endl; + } + } + else + { + // Variable time step. (old update) + // Integrate at least 100 Hz + MT_Scalar timeStep = curtime - m_frames/65536.0; + subStep = timeStep > 0.01 ? 0.01 : timeStep; + num_samples = int(timeStep * 0.01); + if (num_samples < 1) + num_samples = 1; + } + + // Do a physics timestep. + T_ObjectList::iterator i; + if (num_samples > 0) + { + // Do the integration steps per object. + for (int step = 0; step != num_samples; ++step) + { + MT_Scalar time; + if (ticrate > 0.) + time = MT_Scalar(frames + step + 1) * subStep; + else + time = MT_Scalar(m_frames)/65536.0 + MT_Scalar(step + 1)*subStep; + + for (i = m_objectList.begin(); i != m_objectList.end(); ++i) { + (*i)->endFrame(); + // Apply a forcefield (such as gravity) + (*i)->integrateForces(subStep); + // And second we update the object positions by performing + // an integration step for each object + (*i)->integrateMomentum(subStep); + } + + // So now first we let the physics scene respond to + // new forces, velocities set externally. + // The collsion and friction impulses are computed here. + // Collision phase + DT_Test(m_scene, m_respTable); + + // Contact phase + DT_Test(m_scene, m_fixRespTable); + + // Finish this timestep by saving al state information for the next + // timestep and clearing the accumulated forces. + for (i = m_objectList.begin(); i != m_objectList.end(); ++i) { + (*i)->relax(); + (*i)->proceedKinematic(subStep); + (*i)->saveReactionForce(subStep); + (*i)->getNextFrame().setTime(time); + //(*i)->clearForce(); + } + } + } + + if (ticrate > 0) + { + // Interpolate between time steps. + for (i = m_objectList.begin(); i != m_objectList.end(); ++i) + (*i)->interpolate(curtime); + + //only update the m_frames after an actual physics timestep + if (num_samples) + { + m_frames = (unsigned int)(curtime*ticrate) + 1.0; + } + } + else + { + m_frames = (unsigned int)(curtime*65536.0); + } + + return num_samples != 0; +} + +void SM_Scene::notifyCollision(SM_Object *obj1, SM_Object *obj2) +{ + // For each pair of object that collided, call the corresponding callback. + if (m_secondaryRespTable) + DT_CallResponse(m_secondaryRespTable, obj1->getObjectHandle(), obj2->getObjectHandle(), 0); +} + + +SM_Object *SM_Scene::rayTest(void *ignore_client, + const MT_Point3& from, const MT_Point3& to, + MT_Point3& result, MT_Vector3& normal) const { +#ifdef SM_DEBUG_RAYCAST + std::cout << "ray: { " << from << " } - { " << to << " }" << std::endl; +#endif + + DT_Vector3 n, dfrom, dto; + DT_Scalar param; + from.getValue(dfrom); + to.getValue(dto); + SM_Object *hit_object = (SM_Object *) + DT_RayCast(m_scene, ignore_client, dfrom, dto, 1., ¶m, n); + + if (hit_object) { + //result = hit_object->getWorldCoord(from + (to - from)*param); + result = from + (to - from) * param; + normal.setValue(n); +#ifdef SM_DEBUG_RAYCAST + std::cout << "ray: { " << from << " } -> { " << to << " }: { " << result + << " } (" << param << "), normal = { " << normal << " }" << std::endl; +#endif + } + + return hit_object; +} + +void SM_Scene::clearObjectCombinedVelocities() { + + T_ObjectList::iterator i; + + for (i = m_objectList.begin(); i != m_objectList.end(); ++i) { + + (*i)->clearCombinedVelocities(); + + } + +} + + +void SM_Scene::setSecondaryRespTable(DT_RespTableHandle secondaryRespTable) { + m_secondaryRespTable = secondaryRespTable; +} + + +DT_Bool SM_Scene::boing( + void *client_data, + void *object1, + void *object2, + const DT_CollData * +){ + SM_Scene *scene = (SM_Scene *)client_data; + SM_Object *obj1 = (SM_Object *)object1; + SM_Object *obj2 = (SM_Object *)object2; + + scene->notifyCollision(obj1, obj2); // Record this collision for client callbacks + +#ifdef SM_DEBUG_BOING + printf("SM_Scene::boing\n"); +#endif + + return DT_CONTINUE; +} + +SM_Scene::~SM_Scene() +{ + //std::cout << "SM_Scene::~ SM_Scene(): destroy " << this << std::endl; +// if (m_objectList.begin() != m_objectList.end()) +// std::cout << "SM_Scene::~SM_Scene: There are still objects in the Sumo scene!" << std::endl; + for (T_ObjectList::iterator it = m_objectList.begin() ; it != m_objectList.end() ; it++) + delete *it; + + DT_DestroyRespTable(m_respTable); + DT_DestroyRespTable(m_secondaryRespTable); + DT_DestroyRespTable(m_fixRespTable); + DT_DestroyScene(m_scene); +} diff --git a/source/gameengine/Physics/Sumo/Makefile b/source/gameengine/Physics/Sumo/Makefile new file mode 100644 index 00000000000..69efc4d84eb --- /dev/null +++ b/source/gameengine/Physics/Sumo/Makefile @@ -0,0 +1,50 @@ +# +# $Id$ +# +# ***** BEGIN GPL LICENSE BLOCK ***** +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software Foundation, +# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. +# All rights reserved. +# +# The Original Code is: all of this file. +# +# Contributor(s): none yet. +# +# ***** END GPL LICENSE BLOCK ***** +# +# + +SOURCEDIR = source/gameengine/Physics/Sumo +LIBNAME = sumo +DIR = $(OCGDIR)/gameengine/blphys/$(LIBNAME) +DIRS = Fuzzics + +include nan_compile.mk + +CCFLAGS += $(LEVEL_1_CPP_WARNINGS) + +CPPFLAGS += -I$(OPENGL_HEADERS) +CPPFLAGS += -I$(NAN_STRING)/include +CPPFLAGS += -I$(NAN_PYTHON)/include/python$(NAN_PYTHON_VERSION) + +CPPFLAGS += -I$(NAN_FUZZICS)/include -I$(NAN_SUMO) -I$(NAN_MOTO)/include +CPPFLAGS += -I$(NAN_SOLID)/include +CPPFLAGS += -I$(NAN_GUARDEDALLOC)/include +CPPFLAGS += -I../../Physics/common +CPPFLAGS += -I../../Physics/Dummy + +include nan_subdirs.mk diff --git a/source/gameengine/Physics/Sumo/SConscript b/source/gameengine/Physics/Sumo/SConscript new file mode 100644 index 00000000000..a228a986af2 --- /dev/null +++ b/source/gameengine/Physics/Sumo/SConscript @@ -0,0 +1,25 @@ +#!/usr/bin/python +Import ('env') + +sources = ['SumoPHYCallbackBridge.cpp', + 'SumoPhysicsController.cpp', + 'SumoPhysicsEnvironment.cpp', + 'Fuzzics/src/SM_FhObject.cpp', + 'Fuzzics/src/SM_Object.cpp', + 'Fuzzics/src/SM_Scene.cpp', + 'Fuzzics/src/SM_MotionState.cpp' + ] + +incs =['.', + '../common', + 'Fuzzics/include', + '#/intern/moto/include' + ] +incs += [env['BF_SOLID_INC']] + +cflags = [] +if env['OURPLATFORM']=='win32-vc': + cflags.append('/GR') + cflags.append('/O1') + +env.BlenderLib ( 'bf_sumo', sources, incs, [], libtype=['core','player'], priority=[400, 55] , compileflags=cflags) diff --git a/source/gameengine/Physics/Sumo/SumoPHYCallbackBridge.cpp b/source/gameengine/Physics/Sumo/SumoPHYCallbackBridge.cpp new file mode 100644 index 00000000000..1992bbe3421 --- /dev/null +++ b/source/gameengine/Physics/Sumo/SumoPHYCallbackBridge.cpp @@ -0,0 +1,66 @@ +#include "SumoPHYCallbackBridge.h" +#include "PHY_IPhysicsController.h" +#include "SM_Object.h" + + +SumoPHYCallbackBridge::SumoPHYCallbackBridge(void* clientData,PHY_ResponseCallback phyCallback) +:m_orgClientData(clientData), +m_phyCallback(phyCallback) +{ + +} +DT_Bool SumoPHYCallbackBridge::StaticSolidToPHYCallback(void *client_data, + void *client_object1, + void *client_object2, + const DT_CollData *coll_data) +{ + SumoPHYCallbackBridge* bridge = static_cast<SumoPHYCallbackBridge*>(client_data); + bridge->SolidToPHY(client_object1,client_object2,coll_data); + return false; +} + +DT_Bool SumoPHYCallbackBridge::SolidToPHY(void *client_object1, + void *client_object2, + const DT_CollData *coll_data) +{ + + SM_Object* smObject1 = static_cast<SM_Object*>(client_object1); + SM_Object* smObject2 = static_cast<SM_Object*>(client_object2); + + PHY_IPhysicsController* ctrl1 = static_cast<PHY_IPhysicsController*>(smObject1->getPhysicsClientObject()); + PHY_IPhysicsController* ctrl2 = static_cast<PHY_IPhysicsController*>(smObject2->getPhysicsClientObject()); + + if (!ctrl1 || !ctrl2) + { + //todo: check which objects are not linked up properly + return false; + } + if (coll_data) + { + PHY_CollData phyCollData; + + phyCollData.m_point1[0] = coll_data->point1[0]; + phyCollData.m_point1[1] = coll_data->point1[1]; + phyCollData.m_point1[2] = coll_data->point1[2]; + phyCollData.m_point1[3] = 0.f; + + phyCollData.m_point2[0] = coll_data->point2[0]; + phyCollData.m_point2[1] = coll_data->point2[1]; + phyCollData.m_point2[2] = coll_data->point2[2]; + phyCollData.m_point2[3] = 0.f; + + phyCollData.m_normal[0] = coll_data->normal[0]; + phyCollData.m_normal[1] = coll_data->normal[1]; + phyCollData.m_normal[2] = coll_data->normal[2]; + phyCollData.m_normal[3] = 0.f; + + + return m_phyCallback(m_orgClientData, + ctrl1,ctrl2,&phyCollData); + } + + return m_phyCallback(m_orgClientData, + ctrl1,ctrl2,0); + +} + diff --git a/source/gameengine/Physics/Sumo/SumoPHYCallbackBridge.h b/source/gameengine/Physics/Sumo/SumoPHYCallbackBridge.h new file mode 100644 index 00000000000..cc980f3961d --- /dev/null +++ b/source/gameengine/Physics/Sumo/SumoPHYCallbackBridge.h @@ -0,0 +1,28 @@ +#ifndef SUMO_PHY_CALLBACK_BRIDGE_H +#define SUMO_PHY_CALLBACK_BRIDGE_H + +#include <SOLID/SOLID.h> +#include "PHY_DynamicTypes.h" + +class SumoPHYCallbackBridge +{ + void* m_orgClientData; + PHY_ResponseCallback m_phyCallback; + +public: + + SumoPHYCallbackBridge(void* clientData,PHY_ResponseCallback phyCallback); + + static DT_Bool StaticSolidToPHYCallback(void *client_data, + void *client_object1, + void *client_object2, + const DT_CollData *coll_data); + + DT_Bool SolidToPHY(void *client_object1, + void *client_object2, + const DT_CollData *coll_data); + + +}; + +#endif //SUMO_PHY_CALLBACK_BRIDGE_H diff --git a/source/gameengine/Physics/Sumo/SumoPhysicsController.cpp b/source/gameengine/Physics/Sumo/SumoPhysicsController.cpp new file mode 100644 index 00000000000..56caa9236bf --- /dev/null +++ b/source/gameengine/Physics/Sumo/SumoPhysicsController.cpp @@ -0,0 +1,495 @@ +/** + * @file $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ + +#include "SumoPhysicsController.h" +#include "PHY_IMotionState.h" +#include "SM_Object.h" +#include "MT_Quaternion.h" + + +SumoPhysicsController::SumoPhysicsController( + class SM_Scene* sumoScene, + class SM_Object* sumoObj, + class PHY_IMotionState* motionstate, + + bool dyna) + : + m_sumoObj(sumoObj) , + m_sumoScene(sumoScene), + m_bFirstTime(true), + m_bDyna(dyna), + m_MotionState(motionstate) +{ + if (m_sumoObj) + { + + PHY__Vector3 pos1; + getPosition(pos1); + MT_Point3 pos(pos1); + + //temp debugging check + //assert(pos.length() < 100000.f); + + //need this to do the upcast after the solid/sumo collision callback + m_sumoObj->setPhysicsClientObject(this); + //if it is a dyna, register for a callback + m_sumoObj->registerCallback(*this); + } +}; + + + +SumoPhysicsController::~SumoPhysicsController() +{ + if (m_sumoObj) + { + m_sumoScene->remove(*m_sumoObj); + + delete m_sumoObj; + m_sumoObj = NULL; + } +} + +float SumoPhysicsController::getMass() +{ + if (m_sumoObj) + { + const SM_ShapeProps *shapeprops = m_sumoObj->getShapeProps(); + if(shapeprops!=NULL) return shapeprops->m_mass; + } + return 0.f; +} + +bool SumoPhysicsController::SynchronizeMotionStates(float) +{ + if (m_bFirstTime) + { + setSumoTransform(!m_bFirstTime); + m_bFirstTime = false; + } + return false; +} + + + + +void SumoPhysicsController::GetWorldOrientation(MT_Matrix3x3& mat) +{ + float orn[4]; + m_MotionState->getWorldOrientation(orn[0],orn[1],orn[2],orn[3]); + MT_Quaternion quat(orn); + mat.setRotation(quat); + +} + +void SumoPhysicsController::getPosition(PHY__Vector3& pos) const +{ + assert(m_sumoObj); + + pos[0] = m_sumoObj->getPosition()[0]; + pos[1] = m_sumoObj->getPosition()[0]; + pos[2] = m_sumoObj->getPosition()[0]; + + //m_MotionState->getWorldPosition(pos[0],pos[1],pos[2]); +} + +void SumoPhysicsController::GetWorldPosition(MT_Point3& pos) +{ +// assert(m_sumoObj); + +// pos[0] = m_sumoObj->getPosition()[0]; +// pos[1] = m_sumoObj->getPosition()[0]; +// pos[2] = m_sumoObj->getPosition()[0]; + + float worldpos[3]; + m_MotionState->getWorldPosition(worldpos[0],worldpos[1],worldpos[2]); + pos[0]=worldpos[0]; + pos[1]=worldpos[1]; + pos[2]=worldpos[2]; +} + +void SumoPhysicsController::GetWorldScaling(MT_Vector3& scale) +{ + float worldscale[3]; + m_MotionState->getWorldScaling(worldscale[0],worldscale[1],worldscale[2]); + scale[0]=worldscale[0]; + scale[1]=worldscale[1]; + scale[2]=worldscale[2]; +} + + + // kinematic methods +void SumoPhysicsController::RelativeTranslate(float dlocX,float dlocY,float dlocZ,bool local) +{ + if (m_sumoObj) + { + MT_Matrix3x3 mat; + GetWorldOrientation(mat); + MT_Vector3 dloc(dlocX,dlocY,dlocZ); + + MT_Point3 newpos = m_sumoObj->getPosition(); + + newpos += (local ? mat * dloc : dloc); + m_sumoObj->setPosition(newpos); + } + +} +void SumoPhysicsController::RelativeRotate(const float drot[12],bool local) +{ + if (m_sumoObj ) + { + MT_Matrix3x3 drotmat(drot); + MT_Matrix3x3 currentOrn; + GetWorldOrientation(currentOrn); + + m_sumoObj->setOrientation(m_sumoObj->getOrientation()*(local ? + drotmat : (currentOrn.inverse() * drotmat * currentOrn)).getRotation()); + } + +} +void SumoPhysicsController::setOrientation(float quatImag0,float quatImag1,float quatImag2,float quatReal) +{ + m_sumoObj->setOrientation(MT_Quaternion(quatImag0,quatImag1,quatImag2,quatReal)); +} + +void SumoPhysicsController::getOrientation(float &quatImag0,float &quatImag1,float &quatImag2,float &quatReal) +{ + const MT_Quaternion& q = m_sumoObj->getOrientation(); + quatImag0 = q[0]; + quatImag1 = q[1]; + quatImag2 = q[2]; + quatReal = q[3]; +} + +void SumoPhysicsController::setPosition(float posX,float posY,float posZ) +{ + m_sumoObj->setPosition(MT_Point3(posX,posY,posZ)); +} + +void SumoPhysicsController::setScaling(float scaleX,float scaleY,float scaleZ) +{ + if (!m_bDyna) + m_sumoObj->setScaling(MT_Vector3(scaleX,scaleY,scaleZ)); +} + + // physics methods +void SumoPhysicsController::ApplyTorque(float torqueX,float torqueY,float torqueZ,bool local) +{ + if (m_sumoObj) + { + MT_Vector3 torque(torqueX,torqueY,torqueZ); + + MT_Matrix3x3 orn; + GetWorldOrientation(orn); + m_sumoObj->applyTorque(local ? + orn * torque : + torque); + } +} + +void SumoPhysicsController::ApplyForce(float forceX,float forceY,float forceZ,bool local) +{ + if (m_sumoObj) + { + MT_Vector3 force(forceX,forceY,forceZ); + + MT_Matrix3x3 orn; + GetWorldOrientation(orn); + + m_sumoObj->applyCenterForce(local ? + orn * force : + force); + } +} + +void SumoPhysicsController::SetAngularVelocity(float ang_velX,float ang_velY,float ang_velZ,bool local) +{ + if (m_sumoObj) + { + MT_Vector3 ang_vel(ang_velX,ang_velY,ang_velZ); + + MT_Matrix3x3 orn; + GetWorldOrientation(orn); + + m_sumoObj->setExternalAngularVelocity(local ? + orn * ang_vel : + ang_vel); + } +} + +void SumoPhysicsController::SetLinearVelocity(float lin_velX,float lin_velY,float lin_velZ,bool local) +{ + if (m_sumoObj ) + { + MT_Matrix3x3 orn; + GetWorldOrientation(orn); + + MT_Vector3 lin_vel(lin_velX,lin_velY,lin_velZ); + m_sumoObj->setExternalLinearVelocity(local ? + orn * lin_vel : + lin_vel); + } +} + +void SumoPhysicsController::resolveCombinedVelocities(float linvelX,float linvelY,float linvelZ,float angVelX,float angVelY,float angVelZ) +{ + if (m_sumoObj) + m_sumoObj->resolveCombinedVelocities(MT_Vector3(linvelX,linvelY,linvelZ),MT_Vector3(angVelX,angVelY,angVelZ)); +} + + + + +void SumoPhysicsController::applyImpulse(float attachX,float attachY,float attachZ, float impulseX,float impulseY,float impulseZ) +{ + if (m_sumoObj) + { + MT_Point3 attach(attachX,attachY,attachZ); + MT_Vector3 impulse(impulseX,impulseY,impulseZ); + m_sumoObj->applyImpulse(attach,impulse); + } + +} + +void SumoPhysicsController::SuspendDynamics() +{ + m_suspendDynamics=true; + + if (m_sumoObj) + { + m_sumoObj->suspendDynamics(); + m_sumoObj->setLinearVelocity(MT_Vector3(0,0,0)); + m_sumoObj->setAngularVelocity(MT_Vector3(0,0,0)); + m_sumoObj->calcXform(); + } +} + +void SumoPhysicsController::RestoreDynamics() +{ + m_suspendDynamics=false; + + if (m_sumoObj) + { + m_sumoObj->restoreDynamics(); + } +} + + +/** + reading out information from physics +*/ +void SumoPhysicsController::GetLinearVelocity(float& linvX,float& linvY,float& linvZ) +{ + if (m_sumoObj) + { + // get velocity from the physics object (m_sumoObj) + const MT_Vector3& vel = m_sumoObj->getLinearVelocity(); + linvX = vel[0]; + linvY = vel[1]; + linvZ = vel[2]; + } + else + { + linvX = 0.f; + linvY = 0.f; + linvZ = 0.f; + } +} + +/** + GetVelocity parameters are in geometric coordinates (Origin is not center of mass!). +*/ +void SumoPhysicsController::GetVelocity(const float posX,const float posY,const float posZ,float& linvX,float& linvY,float& linvZ) +{ + if (m_sumoObj) + { + MT_Point3 pos(posX,posY,posZ); + // get velocity from the physics object (m_sumoObj) + const MT_Vector3& vel = m_sumoObj->getVelocity(pos); + linvX = vel[0]; + linvY = vel[1]; + linvZ = vel[2]; + } + else + { + linvX = 0.f; + linvY = 0.f; + linvZ = 0.f; + + } +} + +void SumoPhysicsController::getReactionForce(float& forceX,float& forceY,float& forceZ) +{ + const MT_Vector3& force = m_sumoObj->getReactionForce(); + forceX = force[0]; + forceY = force[1]; + forceZ = force[2]; +} + +void SumoPhysicsController::setRigidBody(bool rigid) +{ + m_sumoObj->setRigidBody(rigid); +} + +void SumoPhysicsController::PostProcessReplica(class PHY_IMotionState* motionstate,class PHY_IPhysicsController* parentctrl) +{ + m_MotionState = motionstate; + + SM_Object* dynaparent=0; + SumoPhysicsController* sumoparentctrl = (SumoPhysicsController* )parentctrl; + + if (sumoparentctrl) + { + dynaparent = sumoparentctrl->GetSumoObject(); + } + + SM_Object* orgsumoobject = m_sumoObj; + + + m_sumoObj = new SM_Object( + orgsumoobject->getShapeHandle(), + orgsumoobject->getMaterialProps(), + orgsumoobject->getShapeProps(), + dynaparent); + + m_sumoObj->setRigidBody(orgsumoobject->isRigidBody()); + + m_sumoObj->setMargin(orgsumoobject->getMargin()); + m_sumoObj->setPosition(orgsumoobject->getPosition()); + m_sumoObj->setOrientation(orgsumoobject->getOrientation()); + //if it is a dyna, register for a callback + m_sumoObj->registerCallback(*this); + + m_sumoScene->add(* (m_sumoObj)); +} + +PHY_IMotionState* SumoPhysicsController::GetMotionState() +{ + return m_MotionState; +} + +void SumoPhysicsController::SetSimulatedTime(float) +{ +} + + +void SumoPhysicsController::WriteMotionStateToDynamics(bool) +{ + +} +// this is the actual callback from sumo, and the position/orientation +//is written to the scenegraph, using the motionstate abstraction + +void SumoPhysicsController::do_me() +{ + MT_assert(m_sumoObj); + const MT_Point3& pos = m_sumoObj->getPosition(); + const MT_Quaternion& orn = m_sumoObj->getOrientation(); + + MT_assert(m_MotionState); + m_MotionState->setWorldPosition(pos[0],pos[1],pos[2]); + m_MotionState->setWorldOrientation(orn[0],orn[1],orn[2],orn[3]); +} + + +void SumoPhysicsController::setSumoTransform(bool nondynaonly) +{ + if (!nondynaonly || !m_bDyna) + { + if (m_sumoObj) + { + MT_Point3 pos; + GetWorldPosition(pos); + + m_sumoObj->setPosition(pos); + if (m_bDyna) + { + m_sumoObj->setScaling(MT_Vector3(1,1,1)); + } else + { + MT_Vector3 scale; + GetWorldScaling(scale); + m_sumoObj->setScaling(scale); + } + MT_Matrix3x3 orn; + GetWorldOrientation(orn); + m_sumoObj->setOrientation(orn.getRotation()); + m_sumoObj->calcXform(); + } + } +} + + + // clientinfo for raycasts for example +void* SumoPhysicsController::getNewClientInfo() +{ + if (m_sumoObj) + return m_sumoObj->getClientObject(); + return 0; + +} +void SumoPhysicsController::setNewClientInfo(void* clientinfo) +{ + if (m_sumoObj) + { + SM_ClientObject* clOb = static_cast<SM_ClientObject*> (clientinfo); + m_sumoObj->setClientObject(clOb); + } + +} + +void SumoPhysicsController::calcXform() +{ + if (m_sumoObj) + m_sumoObj->calcXform(); +} + +void SumoPhysicsController::SetMargin(float margin) +{ + if (m_sumoObj) + m_sumoObj->setMargin(margin); +} + +float SumoPhysicsController::GetMargin() const +{ + if (m_sumoObj) + m_sumoObj->getMargin(); + return 0.f; +} + +float SumoPhysicsController::GetRadius() const +{ + if (m_sumoObj && m_sumoObj->getShapeProps()) + { + return m_sumoObj->getShapeProps()->m_radius; + } + return 0.f; + +} diff --git a/source/gameengine/Physics/Sumo/SumoPhysicsController.h b/source/gameengine/Physics/Sumo/SumoPhysicsController.h new file mode 100644 index 00000000000..adf29649f18 --- /dev/null +++ b/source/gameengine/Physics/Sumo/SumoPhysicsController.h @@ -0,0 +1,192 @@ +/** + * @file $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef __SUMO_PHYSICSCONTROLLER_H +#define __SUMO_PHYSICSCONTROLLER_H + +#include "PHY_IPhysicsController.h" +#include "SM_Scene.h" +#include "SM_Callback.h" + +/** + * Sumo Physics Controller, a special kind of a PhysicsController. + * A Physics Controller is a special kind of Scene Graph Transformation Controller. + * Each time the scene graph get's updated, the controller get's a chance + * in the 'Update' method to reflect changes. + * + * Sumo uses the SOLID library for collision detection. + */ +class SumoPhysicsController : public PHY_IPhysicsController , public SM_Callback + + +{ + + +public: + SumoPhysicsController( + class SM_Scene* sumoScene, + class SM_Object* sumoObj, + class PHY_IMotionState* motionstate, + bool dyna); + + virtual ~SumoPhysicsController(); + + /** + * @name Kinematic Methods. + */ + /*@{*/ + virtual void RelativeTranslate(float dlocX,float dlocY,float dlocZ,bool local); + /** + * @param drot a 3x4 matrix. This will treated as a 3x3 rotation matrix. + * @warning RelativeRotate expects a 3x4 matrix. The fourth column is padding. + */ + virtual void RelativeRotate(const float drot[12],bool local); + virtual void getOrientation(float &quatImag0,float &quatImag1,float &quatImag2,float &quatReal); + virtual void setOrientation(float quatImag0,float quatImag1,float quatImag2,float quatReal); + virtual void setPosition(float posX,float posY,float posZ); + virtual void getPosition(PHY__Vector3& pos) const; + + virtual void setScaling(float scaleX,float scaleY,float scaleZ); + /*@}*/ + + /** + * @name Physics Methods + */ + /*@{*/ + virtual void ApplyTorque(float torqueX,float torqueY,float torqueZ,bool local); + virtual void ApplyForce(float forceX,float forceY,float forceZ,bool local); + virtual void SetAngularVelocity(float ang_velX,float ang_velY,float ang_velZ,bool local); + virtual void SetLinearVelocity(float lin_velX,float lin_velY,float lin_velZ,bool local); + virtual void resolveCombinedVelocities(float linvelX,float linvelY,float linvelZ,float angVelX,float angVelY,float angVelZ); + virtual void applyImpulse(float attachX,float attachY,float attachZ, float impulseX,float impulseY,float impulseZ); + virtual void SetActive(bool active){}; + virtual void SuspendDynamics(); + virtual void RestoreDynamics(); + /*@}*/ + + + /** + * reading out information from physics + */ + virtual void GetLinearVelocity(float& linvX,float& linvY,float& linvZ); + /** + * GetVelocity parameters are in geometric coordinates (Origin is not center of mass!). + */ + virtual void GetVelocity(const float posX,const float posY,const float posZ,float& linvX,float& linvY,float& linvZ); + virtual float getMass(); + virtual void getReactionForce(float& forceX,float& forceY,float& forceZ); + virtual void setRigidBody(bool rigid); + + + virtual void PostProcessReplica(class PHY_IMotionState* motionstate,class PHY_IPhysicsController* parentctrl); + + // TODO: remove next line ! + virtual void SetSimulatedTime(float time); + + virtual void WriteDynamicsToMotionState() {}; + virtual void WriteMotionStateToDynamics(bool nondynaonly); + virtual class PHY_IMotionState* GetMotionState(); + + /** + * call from Scene Graph Node to 'update'. + */ + virtual bool SynchronizeMotionStates(float time); + + virtual void calcXform(); + virtual void SetMargin(float margin) ; + virtual float GetMargin() const; + virtual float GetRadius() const ; + virtual void SetRadius(float margin) { SetMargin(margin); } + + + // clientinfo for raycasts for example + virtual void* getNewClientInfo(); + virtual void setNewClientInfo(void* clientinfo); + + float getFriction() { return m_friction;} + float getRestitution() { return m_restitution;} + + /** + * Sumo callback + */ + virtual void do_me(); + + class SM_Object* GetSumoObject () + { + return m_sumoObj; + }; + + void GetWorldOrientation(class MT_Matrix3x3& mat); + void GetWorldPosition(MT_Point3& pos); + void GetWorldScaling(MT_Vector3& scale); + + float GetLinVelocityMin() const { return 0.f; } + void SetLinVelocityMin(float val) { } + float GetLinVelocityMax() const { return 0.f; } + void SetLinVelocityMax(float val) { } + + +// void SetSumoObject(class SM_Object* sumoObj) { +// m_sumoObj = sumoObj; +// } +// void SetSumoScene(class SM_Scene* sumoScene) { +// m_sumoScene = sumoScene; +// } + + void setSumoTransform(bool nondynaonly); + + +private: + class SM_Object* m_sumoObj; + class SM_Scene* m_sumoScene; // needed for replication + bool m_bFirstTime; + bool m_bDyna; + + float m_friction; + float m_restitution; + + + bool m_suspendDynamics; + + bool m_firstTime; + bool m_bFullRigidBody; + bool m_bPhantom; // special flag for objects that are not affected by physics 'resolver' + + // data to calculate fake velocities for kinematic objects (non-dynas) + bool m_bKinematic; + bool m_bPrevKinematic; + + float m_lastTime; + + class PHY_IMotionState* m_MotionState; + + +}; + +#endif //__SUMO_PHYSICSCONTROLLER_H + diff --git a/source/gameengine/Physics/Sumo/SumoPhysicsEnvironment.cpp b/source/gameengine/Physics/Sumo/SumoPhysicsEnvironment.cpp new file mode 100644 index 00000000000..b4daf0a3f80 --- /dev/null +++ b/source/gameengine/Physics/Sumo/SumoPhysicsEnvironment.cpp @@ -0,0 +1,264 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#include <string.h> // memset +#include "SumoPhysicsEnvironment.h" +#include "PHY_IMotionState.h" +#include "SumoPhysicsController.h" +#include "SM_Scene.h" +#include "SumoPHYCallbackBridge.h" +#include <SOLID/SOLID.h> + +SumoPhysicsEnvironment::SumoPhysicsEnvironment() +{ + m_fixedTimeStep = 1.f/60.f; + m_useFixedTimeStep = true; + m_currentTime = 0.f; + + m_sumoScene = new SM_Scene(); +} + + + +SumoPhysicsEnvironment::~SumoPhysicsEnvironment() +{ + delete m_sumoScene; +} + + + +void SumoPhysicsEnvironment::beginFrame() +{ + m_sumoScene->beginFrame(); +} + +void SumoPhysicsEnvironment::endFrame() +{ + m_sumoScene->endFrame(); +} + +void SumoPhysicsEnvironment::setFixedTimeStep(bool useFixedTimeStep,float fixedTimeStep) +{ + m_useFixedTimeStep = useFixedTimeStep; + if (m_useFixedTimeStep) + { + m_fixedTimeStep = fixedTimeStep; + } else + { + m_fixedTimeStep = 0.f; + } + //reset current time ? + m_currentTime = 0.f; +} +float SumoPhysicsEnvironment::getFixedTimeStep() +{ + return m_fixedTimeStep; +} + + +bool SumoPhysicsEnvironment::proceedDeltaTime(double curTime,float timeStep,float interval) +{ + + bool result = false; + if (m_useFixedTimeStep) + { + m_currentTime += timeStep; + float ticrate = 1.f/m_fixedTimeStep; + + result = m_sumoScene->proceed(curTime, ticrate); + } else + { + m_currentTime += timeStep; + result = m_sumoScene->proceed(m_currentTime, timeStep); + } + return result; +} + +void SumoPhysicsEnvironment::setGravity(float x,float y,float z) +{ + m_sumoScene->setForceField(MT_Vector3(x,y,z)); +} + +int SumoPhysicsEnvironment::createConstraint( + class PHY_IPhysicsController* ctrl, + class PHY_IPhysicsController* ctrl2, + PHY_ConstraintType type, + float pivotX,float pivotY,float pivotZ, + float axisX,float axisY,float axisZ, + float axis1X,float axis1Y,float axis1Z, + float axis2X,float axis2Y,float axis2Z, + int flag + ) +{ + int constraintid = 0; + return constraintid; +} + +void SumoPhysicsEnvironment::removeConstraint(int constraintid) +{ + if (constraintid) + { + } +} + +PHY_IPhysicsController* SumoPhysicsEnvironment::rayTest(PHY_IRayCastFilterCallback &filterCallback, + float fromX,float fromY,float fromZ, + float toX,float toY,float toZ) +{ + SumoPhysicsController* ignoreCtr = static_cast<SumoPhysicsController*> (filterCallback.m_ignoreController); + + //collision detection / raytesting + MT_Point3 hit, normal; + PHY_RayCastResult result; + + SM_Object* sm_ignore = 0; + if (ignoreCtr) + sm_ignore = ignoreCtr->GetSumoObject(); + + memset(&result, 0, sizeof(result)); + + SM_Object* smOb = m_sumoScene->rayTest(sm_ignore,MT_Point3(fromX, fromY, fromZ),MT_Point3(toX, toY, toZ), hit, normal); + if (smOb) + { + result.m_controller = (PHY_IPhysicsController *) smOb->getPhysicsClientObject(); + result.m_hitPoint[0] = hit[0]; + result.m_hitPoint[1] = hit[1]; + result.m_hitPoint[2] = hit[2]; + result.m_hitNormal[0] = normal[0]; + result.m_hitNormal[1] = normal[1]; + result.m_hitNormal[2] = normal[2]; + filterCallback.reportHit(&result); + } + return result.m_controller; +} +//gamelogic callbacks +void SumoPhysicsEnvironment::addSensor(PHY_IPhysicsController* ctrl) +{ + SumoPhysicsController* smctrl = dynamic_cast<SumoPhysicsController*>(ctrl); + SM_Object* smObject = smctrl->GetSumoObject(); + assert(smObject); + if (smObject) + { + m_sumoScene->addSensor(*smObject); + } +} +void SumoPhysicsEnvironment::removeSensor(PHY_IPhysicsController* ctrl) +{ + SumoPhysicsController* smctrl = dynamic_cast<SumoPhysicsController*>(ctrl); + SM_Object* smObject = smctrl->GetSumoObject(); + assert(smObject); + if (smObject) + { + m_sumoScene->remove(*smObject); + } +} + + +void SumoPhysicsEnvironment::addTouchCallback(int response_class, PHY_ResponseCallback callback, void *user) +{ + + int sumoRespClass = 0; + + //map PHY_ convention into SM_ convention + switch (response_class) + { + case PHY_FH_RESPONSE: + sumoRespClass = FH_RESPONSE; + break; + case PHY_SENSOR_RESPONSE: + sumoRespClass = SENSOR_RESPONSE; + break; + case PHY_CAMERA_RESPONSE: + sumoRespClass =CAMERA_RESPONSE; + break; + case PHY_OBJECT_RESPONSE: + sumoRespClass = OBJECT_RESPONSE; + break; + case PHY_STATIC_RESPONSE: + sumoRespClass = PHY_STATIC_RESPONSE; + break; + case PHY_BROADPH_RESPONSE: + return; + default: + assert(0); + return; + } + + SumoPHYCallbackBridge* bridge = new SumoPHYCallbackBridge(user,callback); + + m_sumoScene->addTouchCallback(sumoRespClass,SumoPHYCallbackBridge::StaticSolidToPHYCallback,bridge); +} +bool SumoPhysicsEnvironment::requestCollisionCallback(PHY_IPhysicsController* ctrl) +{ + SumoPhysicsController* smctrl = dynamic_cast<SumoPhysicsController*>(ctrl); + MT_assert(smctrl); + SM_Object* smObject = smctrl->GetSumoObject(); + MT_assert(smObject); + if (smObject) + { + //assert(smObject->getPhysicsClientObject() == ctrl); + smObject->setPhysicsClientObject(ctrl); + + m_sumoScene->requestCollisionCallback(*smObject); + return true; + } + return false; +} + +bool SumoPhysicsEnvironment::removeCollisionCallback(PHY_IPhysicsController* ctrl) +{ + // intentionally empty + return false; +} + +PHY_IPhysicsController* SumoPhysicsEnvironment::CreateSphereController(float radius,const PHY__Vector3& position) +{ + DT_ShapeHandle shape = DT_NewSphere(0.0); + SM_Object* ob = new SM_Object(shape,0,0,0); + ob->setPosition(MT_Point3(position)); + //testing + MT_Quaternion rotquatje(MT_Vector3(0,0,1),MT_radians(90)); + ob->setOrientation(rotquatje); + + PHY_IPhysicsController* ctrl = new SumoPhysicsController(m_sumoScene,ob,0,false); + ctrl->SetMargin(radius); + return ctrl; +} +PHY_IPhysicsController* SumoPhysicsEnvironment::CreateConeController(float coneradius,float coneheight) +{ + DT_ShapeHandle shape = DT_NewCone(coneradius,coneheight); + SM_Object* ob = new SM_Object(shape,0,0,0); + ob->setPosition(MT_Point3(0.f,0.f,0.f)); + MT_Quaternion rotquatje(MT_Vector3(0,0,1),MT_radians(90)); + ob->setOrientation(rotquatje); + + PHY_IPhysicsController* ctrl = new SumoPhysicsController(m_sumoScene,ob,0,false); + + return ctrl; +} + diff --git a/source/gameengine/Physics/Sumo/SumoPhysicsEnvironment.h b/source/gameengine/Physics/Sumo/SumoPhysicsEnvironment.h new file mode 100644 index 00000000000..5ae33eb4b0e --- /dev/null +++ b/source/gameengine/Physics/Sumo/SumoPhysicsEnvironment.h @@ -0,0 +1,110 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ +#ifndef _SUMOPhysicsEnvironment +#define _SUMOPhysicsEnvironment + +#include "MT_Scalar.h" + +#include "PHY_IPhysicsEnvironment.h" +class SumoPHYCallbackBridge; +#include <vector> +/** +* Physics Environment takes care of stepping the simulation and is a container for physics entities (rigidbodies,constraints, materials etc.) +* A derived class may be able to 'construct' entities by loading and/or converting +*/ +class SumoPhysicsEnvironment : public PHY_IPhysicsEnvironment +{ + + class SM_Scene* m_sumoScene; + float m_currentTime; + float m_fixedTimeStep; + bool m_useFixedTimeStep; + + std::vector<SumoPHYCallbackBridge*> m_callbacks; + +public: + SumoPhysicsEnvironment(); + virtual ~SumoPhysicsEnvironment(); + virtual void beginFrame(); + virtual void endFrame(); +// Perform an integration step of duration 'timeStep'. + virtual bool proceedDeltaTime(double curTime,float timeStep,float interval); + virtual void setFixedTimeStep(bool useFixedTimeStep,float fixedTimeStep); + virtual float getFixedTimeStep(); + + virtual void setGravity(float x,float y,float z); + virtual int createConstraint(class PHY_IPhysicsController* ctrl,class PHY_IPhysicsController* ctrl2,PHY_ConstraintType type, + float pivotX,float pivotY,float pivotZ, + float axisX,float axisY,float axisZ, + float axis1X=0,float axis1Y=0,float axis1Z=0, + float axis2X=0,float axis2Y=0,float axis2Z=0,int flag=0 + + ); + + virtual void removeConstraint(int constraintid); + + //complex constraint for vehicles + virtual PHY_IVehicle* getVehicleConstraint(int constraintId) + { + return 0; + } + + virtual PHY_IPhysicsController* rayTest(PHY_IRayCastFilterCallback &filterCallback,float fromX,float fromY,float fromZ, float toX,float toY,float toZ); + virtual bool cullingTest(PHY_CullingCallback callback, void* userData, PHY__Vector4 *planes, int nplanes, int occlusionRes) { return false; } + + + //gamelogic callbacks + virtual void addSensor(PHY_IPhysicsController* ctrl); + virtual void removeSensor(PHY_IPhysicsController* ctrl); + virtual void addTouchCallback(int response_class, PHY_ResponseCallback callback, void *user); + virtual bool requestCollisionCallback(PHY_IPhysicsController* ctrl); + virtual bool removeCollisionCallback(PHY_IPhysicsController* ctrl); + virtual PHY_IPhysicsController* CreateSphereController(float radius,const PHY__Vector3& position); + virtual PHY_IPhysicsController* CreateConeController(float coneradius,float coneheight); + + virtual float getConstraintParam(int constraintId,int param) + { + return 0.f; + } + virtual void setConstraintParam(int constraintId,int param,float value,float value1) + { + } + SM_Scene* GetSumoScene() + { + return m_sumoScene; + } + +protected: + // 60Hz (Default) + static MT_Scalar PhysicsTicRate; + +}; + +#endif //_SUMOPhysicsEnvironment + diff --git a/source/gameengine/Physics/Sumo/convert.txt b/source/gameengine/Physics/Sumo/convert.txt new file mode 100644 index 00000000000..81f8f602cde --- /dev/null +++ b/source/gameengine/Physics/Sumo/convert.txt @@ -0,0 +1,35 @@ +static DT_ShapeHandle CreateShapeFromMesh(RAS_MeshObject* meshobj) +{ + DT_ShapeHandle shape = DT_NewComplexShape(); + int numpolys = meshobj->NumPolygons(); + int numvalidpolys = 0; + + for (int p=0; p<numpolys; p++) + { + RAS_Polygon* poly = meshobj->GetPolygon(p); + + // only add polygons that have the collisionflag set + if (poly->IsCollider()) + { + DT_Begin(); + for (int v=0; v<poly->VertexCount(); v++) { + MT_Point3 pt = meshobj->GetVertex(poly->GetVertexIndexBase().m_vtxarray, + poly->GetVertexIndexBase().m_indexarray[v], + poly->GetMaterial()->GetPolyMaterial())->xyz(); + DT_Vertex(pt[0],pt[1],pt[2]); + } + DT_End(); + + numvalidpolys++; + } + } + + DT_EndComplexShape(); + + if (numvalidpolys==0) { + delete shape; + return NULL; + } else { + return shape; + } +} diff --git a/source/gameengine/Physics/Sumo/include/interpolator.h b/source/gameengine/Physics/Sumo/include/interpolator.h new file mode 100644 index 00000000000..055c242edc7 --- /dev/null +++ b/source/gameengine/Physics/Sumo/include/interpolator.h @@ -0,0 +1,27 @@ +#ifndef INTERPOLATOR_H +#define INTERPOLATOR_H + +#include "solid_types.h" + +#ifdef __cplusplus +extern "C" { +#endif + +DT_DECLARE_HANDLE(IP_IpoHandle); + +typedef struct IP_ControlPoint { + DT_Scalar m_key; + DT_Scalar m_keyValue; +} IP_ControlPoint; + +IP_IpoHandle IP_CreateLinear(const IP_ControlPoint *cpoints, int num_cpoints); + +void IP_DeleteInterpolator(IP_IpoHandle ipo); + +DT_Scalar IP_GetValue(IP_IpoHandle ipo, DT_Scalar key); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/source/gameengine/Physics/common/Makefile b/source/gameengine/Physics/common/Makefile index f2dd0134b71..e3edd426c36 100644 --- a/source/gameengine/Physics/common/Makefile +++ b/source/gameengine/Physics/common/Makefile @@ -40,7 +40,7 @@ CPPFLAGS += -I$(NAN_STRING)/include CPPFLAGS += -I$(NAN_SOUNDSYSTEM)/include CPPFLAGS += -I$(NAN_PYTHON)/include/python$(NAN_PYTHON_VERSION) -CPPFLAGS += -I$(NAN_FUZZICS)/include -I$(NAN_MOTO)/include +CPPFLAGS += -I$(NAN_FUZZICS)/include -I$(NAN_SUMO)/include -I$(NAN_MOTO)/include CPPFLAGS += -I../../blender # these two needed because of blenkernel CPPFLAGS += -I../../blender/makesdna diff --git a/source/gameengine/SConscript b/source/gameengine/SConscript index 592b138583f..864e4c3ebee 100644 --- a/source/gameengine/SConscript +++ b/source/gameengine/SConscript @@ -18,5 +18,13 @@ SConscript(['BlenderRoutines/SConscript', 'VideoTexture/SConscript' ]) +if env['WITH_BF_SOLID']: + SConscript(['Physics/Sumo/SConscript']) + if env['WITH_BF_PLAYER']: SConscript(['GamePlayer/SConscript']) + +#if user_options_dict['USE_PHYSICS'] == 'solid': +# SConscript(['Physics/Sumo/SConscript']) +#elif user_options_dict['USE_PHYSICS'] == 'ode': +# SConscript(['Physics/BlOde/SConscript']) diff --git a/source/gameengine/VideoTexture/FilterBlueScreen.cpp b/source/gameengine/VideoTexture/FilterBlueScreen.cpp index 6d26e5b6d35..6b23105a278 100644 --- a/source/gameengine/VideoTexture/FilterBlueScreen.cpp +++ b/source/gameengine/VideoTexture/FilterBlueScreen.cpp @@ -81,17 +81,17 @@ static int setColor (PyFilter * self, PyObject * value, void * closure) { // check validity of parameter if (value == NULL || !PySequence_Check(value) || PySequence_Length(value) != 3 - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 0)) - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 1)) - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 2))) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 0)) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 1)) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 2))) { PyErr_SetString(PyExc_TypeError, "The value must be a sequence of 3 ints"); return -1; } // set color - getFilter(self)->setColor((unsigned char)(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 0))), - (unsigned char)(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 1))), - (unsigned char)(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 2)))); + getFilter(self)->setColor((unsigned char)(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 0))), + (unsigned char)(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 1))), + (unsigned char)(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 2)))); // success return 0; } @@ -108,15 +108,15 @@ static int setLimits (PyFilter * self, PyObject * value, void * closure) { // check validity of parameter if (value == NULL || !PySequence_Check(value) || PySequence_Length(value) != 2 - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 0)) - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 1))) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 0)) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 1))) { PyErr_SetString(PyExc_TypeError, "The value must be a sequence of 2 ints"); return -1; } // set limits - getFilter(self)->setLimits((unsigned short)(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 0))), - (unsigned short)(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 1)))); + getFilter(self)->setLimits((unsigned short)(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 0))), + (unsigned short)(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 1)))); // success return 0; } diff --git a/source/gameengine/VideoTexture/FilterColor.cpp b/source/gameengine/VideoTexture/FilterColor.cpp index eb86f520e02..5ff1f7f11ce 100644 --- a/source/gameengine/VideoTexture/FilterColor.cpp +++ b/source/gameengine/VideoTexture/FilterColor.cpp @@ -147,10 +147,10 @@ static int setMatrix (PyFilter * self, PyObject * value, void * closure) for (int c = 0; valid && c < 5; ++c) { // item must be int - valid = PyLong_Check(PySequence_Fast_GET_ITEM(row, c)); + valid = PyInt_Check(PySequence_Fast_GET_ITEM(row, c)); // if it is valid, save it in matrix if (valid) - mat[r][c] = short(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(row, c))); + mat[r][c] = short(PyInt_AsLong(PySequence_Fast_GET_ITEM(row, c))); } } // if parameter is not valid, report error @@ -286,10 +286,10 @@ static int setLevels (PyFilter * self, PyObject * value, void * closure) for (int c = 0; valid && c < 2; ++c) { // item must be int - valid = PyLong_Check(PySequence_Fast_GET_ITEM(row, c)); + valid = PyInt_Check(PySequence_Fast_GET_ITEM(row, c)); // if it is valid, save it in matrix if (valid) - lev[r][c] = (unsigned short)(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(row, c))); + lev[r][c] = (unsigned short)(PyInt_AsLong(PySequence_Fast_GET_ITEM(row, c))); } } // if parameter is not valid, report error diff --git a/source/gameengine/VideoTexture/FilterNormal.cpp b/source/gameengine/VideoTexture/FilterNormal.cpp index 002be6c3189..9a2b1e90d5a 100644 --- a/source/gameengine/VideoTexture/FilterNormal.cpp +++ b/source/gameengine/VideoTexture/FilterNormal.cpp @@ -72,13 +72,13 @@ static PyObject * getColor (PyFilter * self, void * closure) static int setColor (PyFilter * self, PyObject * value, void * closure) { // check validity of parameter - if (value == NULL || !PyLong_Check(value)) + if (value == NULL || !PyInt_Check(value)) { PyErr_SetString(PyExc_TypeError, "filt.colorIdx = int: VideoTexture.FilterNormal, expected the value must be a int"); return -1; } // set color index - getFilter(self)->setColor((unsigned short)(PyLong_AsSsize_t(value))); + getFilter(self)->setColor((unsigned short)(PyInt_AsLong(value))); // success return 0; } diff --git a/source/gameengine/VideoTexture/ImageRender.cpp b/source/gameengine/VideoTexture/ImageRender.cpp index d8be08e0eb5..c4fb1fefd9c 100644 --- a/source/gameengine/VideoTexture/ImageRender.cpp +++ b/source/gameengine/VideoTexture/ImageRender.cpp @@ -331,19 +331,19 @@ static int setBackground (PyImage * self, PyObject * value, void * closure) { // check validity of parameter if (value == NULL || !PySequence_Check(value) || PySequence_Length(value) != 4 - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 0)) - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 1)) - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 2)) - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 3))) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 0)) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 1)) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 2)) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 3))) { PyErr_SetString(PyExc_TypeError, "The value must be a sequence of 4 integer between 0 and 255"); return -1; } // set background color - getImageRender(self)->setBackground((unsigned char)(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 0))), - (unsigned char)(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 1))), - (unsigned char)(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 2))), - (unsigned char)(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 3)))); + getImageRender(self)->setBackground((unsigned char)(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 0))), + (unsigned char)(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 1))), + (unsigned char)(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 2))), + (unsigned char)(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 3)))); // success return 0; } diff --git a/source/gameengine/VideoTexture/ImageViewport.cpp b/source/gameengine/VideoTexture/ImageViewport.cpp index 55b14396280..d2c23e758f6 100644 --- a/source/gameengine/VideoTexture/ImageViewport.cpp +++ b/source/gameengine/VideoTexture/ImageViewport.cpp @@ -218,16 +218,16 @@ static int ImageViewport_setPosition (PyImage * self, PyObject * value, void * c { // check validity of parameter if (value == NULL || !PySequence_Check(value) || PySequence_Length(value) != 2 - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 0)) - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 1))) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 0)) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 1))) { PyErr_SetString(PyExc_TypeError, "The value must be a sequence of 2 ints"); return -1; } // set position GLint pos [] = { - GLint(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 0))), - GLint(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 1))) + GLint(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 0))), + GLint(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 1))) }; getImageViewport(self)->setPosition(pos); // success @@ -246,16 +246,16 @@ int ImageViewport_setCaptureSize (PyImage * self, PyObject * value, void * closu { // check validity of parameter if (value == NULL || !PySequence_Check(value) || PySequence_Length(value) != 2 - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 0)) - || !PyLong_Check(PySequence_Fast_GET_ITEM(value, 1))) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 0)) + || !PyInt_Check(PySequence_Fast_GET_ITEM(value, 1))) { PyErr_SetString(PyExc_TypeError, "The value must be a sequence of 2 ints"); return -1; } // set capture size short size [] = { - short(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 0))), - short(PyLong_AsSsize_t(PySequence_Fast_GET_ITEM(value, 1))) + short(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 0))), + short(PyInt_AsLong(PySequence_Fast_GET_ITEM(value, 1))) }; getImageViewport(self)->setCaptureSize(size); // success diff --git a/source/gameengine/VideoTexture/VideoBase.cpp b/source/gameengine/VideoTexture/VideoBase.cpp index 5de7a9e80a9..5d449a158d8 100644 --- a/source/gameengine/VideoTexture/VideoBase.cpp +++ b/source/gameengine/VideoTexture/VideoBase.cpp @@ -167,13 +167,13 @@ PyObject * Video_getRepeat (PyImage * self, void * closure) int Video_setRepeat (PyImage * self, PyObject * value, void * closure) { // check validity of parameter - if (value == NULL || !PyLong_Check(value)) + if (value == NULL || !PyInt_Check(value)) { PyErr_SetString(PyExc_TypeError, "The value must be an int"); return -1; } // set repeat - getVideo(self)->setRepeat(int(PyLong_AsSsize_t(value))); + getVideo(self)->setRepeat(int(PyInt_AsLong(value))); // success return 0; } diff --git a/source/gameengine/VideoTexture/VideoFFmpeg.cpp b/source/gameengine/VideoTexture/VideoFFmpeg.cpp index cf4ea88c1b5..1a5481488c0 100644 --- a/source/gameengine/VideoTexture/VideoFFmpeg.cpp +++ b/source/gameengine/VideoTexture/VideoFFmpeg.cpp @@ -1095,13 +1095,13 @@ PyObject * VideoFFmpeg_getPreseek (PyImage *self, void * closure) int VideoFFmpeg_setPreseek (PyImage * self, PyObject * value, void * closure) { // check validity of parameter - if (value == NULL || !PyLong_Check(value)) + if (value == NULL || !PyInt_Check(value)) { PyErr_SetString(PyExc_TypeError, "The value must be an integer"); return -1; } // set preseek - getFFmpeg(self)->setPreseek(PyLong_AsSsize_t(value)); + getFFmpeg(self)->setPreseek(PyInt_AsLong(value)); // success return 0; } diff --git a/source/gameengine/VideoTexture/blendVideoTex.cpp b/source/gameengine/VideoTexture/blendVideoTex.cpp index 22171f69321..dad52a426b6 100644 --- a/source/gameengine/VideoTexture/blendVideoTex.cpp +++ b/source/gameengine/VideoTexture/blendVideoTex.cpp @@ -67,7 +67,7 @@ static PyObject * getMaterialID (PyObject *self, PyObject *args) // get last error description static PyObject * getLastError (PyObject *self, PyObject *args) { - return PyUnicode_FromString(Exception::m_lastError.c_str()); + return PyString_FromString(Exception::m_lastError.c_str()); } // set log file diff --git a/source/nan_compile.mk b/source/nan_compile.mk index bc264fe5c1d..bd6dd6e1baa 100644 --- a/source/nan_compile.mk +++ b/source/nan_compile.mk @@ -71,6 +71,21 @@ DBG_CCFLAGS += -g # OS dependent parts --------------------------------------------------- +ifeq ($(OS),beos) + CC = gcc + CCC = g++ + CFLAGS += -pipe -fPIC -funsigned-char -fno-strict-aliasing + CCFLAGS += -pipe -fPIC -funsigned-char -fno-strict-aliasing + REL_CFLAGS += -O2 + REL_CCFLAGS += -O2 + NAN_DEPEND = true + OPENGL_HEADERS = . + CPPFLAGS += -D__BeOS + AR = ar + ARFLAGS = ruv + ARFLAGSQUIET = ru +endif + ifeq ($(OS),darwin) CC = gcc CCC = g++ diff --git a/source/nan_definitions.mk b/source/nan_definitions.mk index 91f90525c1e..b9e623ed4e4 100644 --- a/source/nan_definitions.mk +++ b/source/nan_definitions.mk @@ -91,6 +91,7 @@ endif export BF_PROFILE ?= false export NAN_USE_BULLET ?= true export NAN_BULLET2 ?= $(LCGDIR)/bullet2 + export NAN_SUMO ?= $(SRCHOME)/gameengine/Physics/Sumo export NAN_FUZZICS ?= $(SRCHOME)/gameengine/Physics/Sumo/Fuzzics export NAN_BLENKEY ?= $(LCGDIR)/blenkey export NAN_DECIMATION ?= $(LCGDIR)/decimation @@ -130,6 +131,45 @@ endif endif # Platform Dependent settings go below: + ifeq ($(OS),beos) + + export ID = $(USER) + export HOST = $(HOSTNAME) + export NAN_PYTHON ?= $(LCGDIR)/python + export NAN_PYTHON_VERSION ?= 2.3 + export NAN_PYTHON_BINARY ?= $(NAN_PYTHON)/bin/python$(NAN_PYTHON_VERSION) + export NAN_PYTHON_LIB ?= $(NAN_PYTHON)/lib/python$(NAN_PYTHON_VERSION)/config/libpython$(NAN_PYTHON_VERSION).a + export NAN_OPENAL ?= $(LCGDIR)/openal + export NAN_JPEG ?= $(LCGDIR)/jpeg + export NAN_PNG ?= $(LCGDIR)/png + export NAN_TIFF ?= $(LCGDIR)/tiff + export NAN_ODE ?= $(LCGDIR)/ode + export NAN_TERRAPLAY ?= $(LCGDIR)/terraplay + export NAN_MESA ?= /usr/src/Mesa-3.1 + export NAN_ZLIB ?= $(LCGDIR)/zlib + export NAN_NSPR ?= $(LCGDIR)/nspr + export NAN_FREETYPE ?= $(LCGDIR)/freetype + export NAN_GETTEXT ?= $(LCGDIR)/gettext + export NAN_SDL ?= $(shell sdl-config --prefix) + export NAN_SDLLIBS ?= $(shell sdl-config --libs) + export NAN_SDLCFLAGS ?= $(shell sdl-config --cflags) + + # Uncomment the following line to use Mozilla inplace of netscape + # CPPFLAGS +=-DMOZ_NOT_NET + # Location of MOZILLA/Netscape header files... + export NAN_MOZILLA_INC ?= $(LCGDIR)/mozilla/include + export NAN_MOZILLA_LIB ?= $(LCGDIR)/mozilla/lib/ + # Will fall back to look in NAN_MOZILLA_INC/nspr and NAN_MOZILLA_LIB + # if this is not set. + + export NAN_BUILDINFO ?= true + # Be paranoid regarding library creation (do not update archives) + export NAN_PARANOID ?= true + + # l10n + #export INTERNATIONAL ?= true + + else ifeq ($(OS),darwin) export ID = $(shell whoami) @@ -549,6 +589,7 @@ endif endif # irix endif # freebsd endif # darwin + endif # beos endif # CONFIG_GUESS diff --git a/source/nan_link.mk b/source/nan_link.mk index 63c9a578498..42b17b425b3 100644 --- a/source/nan_link.mk +++ b/source/nan_link.mk @@ -49,6 +49,10 @@ endif # default (overriden by windows) SOEXT = .so +ifeq ($(OS),beos) + LLIBS = -L/boot/develop/lib/x86/ -lGL -lbe -L/boot/home/config/lib/ +endif + ifeq ($(OS),darwin) LLIBS += -lGLU -lGL LLIBS += -lz -lstdc++ |