From 67712c10c4ff3cad574c5daed0e22b30dc769bad Mon Sep 17 00:00:00 2001 From: Campbell Barton Date: Tue, 6 Sep 2011 00:12:34 +0000 Subject: fix for doc building after pepper merge, also WIP tips/tricks. --- doc/python_api/rst/info_tips_and_tricks.rst | 118 +++++++++++++++++++++++----- doc/python_api/sphinx_doc_gen.py | 1 + 2 files changed, 98 insertions(+), 21 deletions(-) diff --git a/doc/python_api/rst/info_tips_and_tricks.rst b/doc/python_api/rst/info_tips_and_tricks.rst index bd5faf000c8..f4e68a4516c 100644 --- a/doc/python_api/rst/info_tips_and_tricks.rst +++ b/doc/python_api/rst/info_tips_and_tricks.rst @@ -1,34 +1,112 @@ -############### +*************** Tips and Tricks -############### +*************** Some of these are just python features that scripters may not have thaught to use with blender. -**************** Use The Terminal -**************** +================ + +When writing python scripts, its useful to have a terminal open, this is not the built-in python console but a terminal application which is used to start blender. + +There are 3 main uses for the terminal, these are: + +* You can see the output of `print()` as you're script runs, which is useful to view debug info. + +* The error tracebacks are printed in full to the terminal which wont always generate an error popup in blenders user interface (depending on how the script is executed). + +* If the script runs for too long or you accidentally enter an infinate loop, Ctrl+C in the terminal (Ctrl+Break on Windows) will quit the script early. + +.. note:: + For Linux and OSX users this means starting the terminal first, then running blender from within it. On Windows the terminal can be enabled from the help menu. -For Linux and OSX users this means starting the terminal first, then running blender from within it. on Windows the terminal can be enabled from the help menu. -******************** Run External Scripts -******************** +==================== + +Blenders text editor is fine for edits and writing small tests but it is not a full featured editor so for larger projects you'll probably want to use an external editor. + +Editing a text file externally and having the same text open in blender does work but isn't that optimal so here are 2 ways you can easily use an external file from blender. + + +Executing External Scripts +^^^^^^^^^^^^^^^^^^^^^^^^^^ + +This is the equivilent to running the script directly, referencing a scripts path from a 2 line textblock. + +.. code-block:: + + filename = "/full/path/to/myscript.py" + exec(compile(open(filename).read(), filename, 'exec')) + + +You might also want to reference the file relative to the blend file. + +.. code-block:: + + filename = "/full/path/to/script.py" + exec(compile(open(filename).read(), filename, 'exec')) + + +You might want to reference a script thats at the same location as the blend file. + +.. code-block:: + + import bpy + import os + + filename = os.path.join(os.path.basename(bpy.data.filepath), "myscript.py") + exec(compile(open(filename).read(), filename, 'exec')) + + +Executing Modules +^^^^^^^^^^^^^^^^^ + +This example shows loading a script in as a module and executing a module function. + +.. code-block:: + + import myscript + import imp + + imp.reload(myscript) + myscript.main() + + +Notice that the script is reloaded every time, this forces an update, normally the module stays cached in `sys.modules`. + +The main difference between this and executing the script directly is it has to call a function in the module, in this case `main()` but it can be any function, an advantage with this is you can pass argumnents to the function from this small script which is often useful for testing differnt settings quickly. + +The other issue with this is the script has to be in pythons module search path. +While this is not best practice - for testing you can extend the search path, this example adds the current blend files directory to the search path, then loads the script as a module. + +.. code-block:: + + import sys + import os + impory bpy + + blend_dir = os.path.basename(bpy.data.filepath) + if blend_dir not in sys.path: + sys.path.append(blend_dir) + + import myscript + import imp + imp.reload(myscript) + myscript.main() -****************** Don't Use Blender! -****************** +================== -****************** Use External Tools -****************** +================== -************** Bundled Python -************** +============== Blender from blender.org includes a compleate python installation on all platforms, this has the disadvantage that any extensions you have installed in you're systems python wont be found by blender. @@ -38,20 +116,18 @@ There are 2 ways around this: * copy the extensions into blender's python subdirectry so blender can access them, you could also copy the entire python installation into blenders subdirectory, replacing the one blender comes with. This works as long as the python versions match and the paths are created in the same location relative locations. Doing this has the advantage that you can redistribute this bundle to others with blender and/or the game player, including any extensions you rely on. -******** + Advanced -******** +======== -=================== Blender as a module -=================== +------------------- -============================ Python Safety (Build Option) -============================ +---------------------------- + -================= CTypes in Blender -================= +----------------- diff --git a/doc/python_api/sphinx_doc_gen.py b/doc/python_api/sphinx_doc_gen.py index e378dd19e73..661d41af4ef 100644 --- a/doc/python_api/sphinx_doc_gen.py +++ b/doc/python_api/sphinx_doc_gen.py @@ -578,6 +578,7 @@ def pycontext2sphinx(BASEPATH): "sequences": ("Sequence", True), "smoke": ("SmokeModifier", False), "soft_body": ("SoftBodyModifier", False), + "speaker": ("Speaker", False), "texture": ("Texture", False), "texture_slot": ("MaterialTextureSlot", False), "vertex_paint_object": ("Object", False), -- cgit v1.2.3 From fa32395b33f084d5c6c9d8026fd7d53335c9b41a Mon Sep 17 00:00:00 2001 From: Campbell Barton Date: Tue, 6 Sep 2011 00:41:28 +0000 Subject: more minor doc fixes --- doc/python_api/rst/bgl.rst | 90 +++++++++++++++++----------------- doc/python_api/rst/info_quickstart.rst | 2 +- 2 files changed, 46 insertions(+), 46 deletions(-) diff --git a/doc/python_api/rst/bgl.rst b/doc/python_api/rst/bgl.rst index 5f3158bf5dd..61400351d16 100644 --- a/doc/python_api/rst/bgl.rst +++ b/doc/python_api/rst/bgl.rst @@ -56,9 +56,9 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type n: int :arg n: Specifies the number of textures to be queried. - :type textures: :class:`Buffer` object I{type GL_INT} + :type textures: :class:`bgl.Buffer` object I{type GL_INT} :arg textures: Specifies an array containing the names of the textures to be queried - :type residences: :class:`Buffer` object I{type GL_INT}(boolean) + :type residences: :class:`bgl.Buffer` object I{type GL_INT}(boolean) :arg residences: An array in which the texture residence status in returned. The residence status of a texture named by an element of textures is returned in the corresponding element of residences. @@ -101,7 +101,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type xmove, ymove: float :arg xmove, ymove: Specify the x and y offsets to be added to the current raster position after the bitmap is drawn. - :type bitmap: :class:`Buffer` object I{type GL_BYTE} + :type bitmap: :class:`bgl.Buffer` object I{type GL_BYTE} :arg bitmap: Specifies the address of the bitmap image. @@ -139,7 +139,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg n: Specifies the number of display lists to be executed. :type type: Enumerated constant :arg type: Specifies the type of values in lists. - :type lists: :class:`Buffer` object + :type lists: :class:`bgl.Buffer` object :arg lists: Specifies the address of an array of name offsets in the display list. The pointer type is void because the offsets can be bytes, shorts, ints, or floats, depending on the value of type. @@ -217,7 +217,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type plane: Enumerated constant :arg plane: Specifies which clipping plane is being positioned. - :type equation: :class:`Buffer` object I{type GL_FLOAT}(double) + :type equation: :class:`bgl.Buffer` object I{type GL_FLOAT}(double) :arg equation: Specifies the address of an array of four double- precision floating-point values. These values are interpreted as a plane equation. @@ -340,7 +340,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type n: int :arg n: Specifies the number of textures to be deleted - :type textures: :class:`Buffer` I{GL_INT} + :type textures: :class:`bgl.Buffer` I{GL_INT} :arg textures: Specifies an array of textures to be deleted @@ -413,7 +413,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg format: Specifies the format of the pixel data. :type type: Enumerated constant :arg type: Specifies the data type for pixels. - :type pixels: :class:`Buffer` object + :type pixels: :class:`bgl.Buffer` object :arg pixels: Specifies a pointer to the pixel data. @@ -512,7 +512,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type type: Enumerated constant :arg type: Specifies a symbolic constant that describes the information that will be returned for each vertex. - :type buffer: :class:`Buffer` object I{GL_FLOAT} + :type buffer: :class:`bgl.Buffer` object I{GL_FLOAT} :arg buffer: Returns the feedback data. @@ -592,7 +592,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type n: int :arg n: Specifies the number of textures name to be generated. - :type textures: :class:`Buffer` object I{type GL_INT} + :type textures: :class:`bgl.Buffer` object I{type GL_INT} :arg textures: Specifies an array in which the generated textures names are stored. @@ -620,7 +620,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg plane: Specifies a clipping plane. The number of clipping planes depends on the implementation, but at least six clipping planes are supported. They are identified by symbolic names of the form GL_CLIP_PLANEi where 0 < i < GL_MAX_CLIP_PLANES. - :type equation: :class:`Buffer` object I{type GL_FLOAT} + :type equation: :class:`bgl.Buffer` object I{type GL_FLOAT} :arg equation: Returns four float (double)-precision values that are the coefficients of the plane equation of plane in eye coordinates. The initial value is (0, 0, 0, 0). @@ -646,7 +646,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. names of the form GL_LIGHTi where 0 < i < GL_MAX_LIGHTS. :type pname: Enumerated constant :arg pname: Specifies a light source parameter for light. - :type params: :class:`Buffer` object. Depends on function prototype. + :type params: :class:`bgl.Buffer` object. Depends on function prototype. :arg params: Returns the requested data. @@ -662,7 +662,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg target: Specifies the symbolic name of a map. :type query: Enumerated constant :arg query: Specifies which parameter to return. - :type v: :class:`Buffer` object. Depends on function prototype. + :type v: :class:`bgl.Buffer` object. Depends on function prototype. :arg v: Returns the requested data. @@ -679,7 +679,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. representing the front and back materials, respectively. :type pname: Enumerated constant :arg pname: Specifies the material parameter to return. - :type params: :class:`Buffer` object. Depends on function prototype. + :type params: :class:`bgl.Buffer` object. Depends on function prototype. :arg params: Returns the requested data. @@ -693,7 +693,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type map: Enumerated constant :arg map: Specifies the name of the pixel map to return. - :type values: :class:`Buffer` object. Depends on function prototype. + :type values: :class:`bgl.Buffer` object. Depends on function prototype. :arg values: Returns the pixel map contents. @@ -703,7 +703,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. .. seealso:: `OpenGL Docs `_ - :type mask: :class:`Buffer` object I{type GL_BYTE} + :type mask: :class:`bgl.Buffer` object I{type GL_BYTE} :arg mask: Returns the stipple pattern. The initial value is all 1's. @@ -730,7 +730,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg target: Specifies a texture environment. Must be GL_TEXTURE_ENV. :type pname: Enumerated constant :arg pname: Specifies the symbolic name of a texture environment parameter. - :type params: :class:`Buffer` object. Depends on function prototype. + :type params: :class:`bgl.Buffer` object. Depends on function prototype. :arg params: Returns the requested data. @@ -746,7 +746,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg coord: Specifies a texture coordinate. :type pname: Enumerated constant :arg pname: Specifies the symbolic name of the value(s) to be returned. - :type params: :class:`Buffer` object. Depends on function prototype. + :type params: :class:`bgl.Buffer` object. Depends on function prototype. :arg params: Returns the requested data. @@ -765,7 +765,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg format: Specifies a pixel format for the returned data. :type type: Enumerated constant :arg type: Specifies a pixel type for the returned data. - :type pixels: :class:`Buffer` object. + :type pixels: :class:`bgl.Buffer` object. :arg pixels: Returns the texture image. Should be a pointer to an array of the type specified by type @@ -785,7 +785,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. Level 0 is the base image level. Level n is the nth mipmap reduction image. :type pname: Enumerated constant :arg pname: Specifies the symbolic name of a texture parameter. - :type params: :class:`Buffer` object. Depends on function prototype. + :type params: :class:`bgl.Buffer` object. Depends on function prototype. :arg params: Returns the requested data. @@ -801,7 +801,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg target: Specifies the symbolic name of the target texture. :type pname: Enumerated constant :arg pname: Specifies the symbolic name the target texture. - :type params: :class:`Buffer` object. Depends on function prototype. + :type params: :class:`bgl.Buffer` object. Depends on function prototype. :arg params: Returns the texture parameters. @@ -826,7 +826,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. .. seealso:: `OpenGL Docs `_ - :type c: :class:`Buffer` object. Depends on function prototype. + :type c: :class:`bgl.Buffer` object. Depends on function prototype. :arg c: Specifies a pointer to a one element array that contains the new value for the current color index. @@ -956,7 +956,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. .. seealso:: `OpenGL Docs `_ - :type m: :class:`Buffer` object. Depends on function prototype. + :type m: :class:`bgl.Buffer` object. Depends on function prototype. :arg m: Specifies a pointer to 16 consecutive values, which are used as the elements of a 4x4 column-major matrix. @@ -1002,7 +1002,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. occupy contiguous memory locations. :type order: int :arg order: Specifies the number of control points. Must be positive. - :type points: :class:`Buffer` object. Depends on function prototype. + :type points: :class:`bgl.Buffer` object. Depends on function prototype. :arg points: Specifies a pointer to the array of control points. @@ -1043,7 +1043,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type vorder: int :arg vorder: Specifies the dimension of the control point array in the v axis. Must be positive. The initial value is 1. - :type points: :class:`Buffer` object. Depends on function prototype. + :type points: :class:`bgl.Buffer` object. Depends on function prototype. :arg points: Specifies a pointer to the array of control points. @@ -1103,7 +1103,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. .. seealso:: `OpenGL Docs `_ - :type m: :class:`Buffer` object. Depends on function prototype. + :type m: :class:`bgl.Buffer` object. Depends on function prototype. :arg m: Points to 16 consecutive values that are used as the elements of a 4x4 column major matrix. @@ -1132,7 +1132,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type nx, ny, nz: Depends on function prototype. (non - 'v' prototypes only) :arg nx, ny, nz: Specify the x, y, and z coordinates of the new current normal. The initial value of the current normal is the unit vector, (0, 0, 1). - :type v: :class:`Buffer` object. Depends on function prototype. ('v' prototypes) + :type v: :class:`bgl.Buffer` object. Depends on function prototype. ('v' prototypes) :arg v: Specifies a pointer to an array of three elements: the x, y, and z coordinates of the new current normal. @@ -1177,7 +1177,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg map: Specifies a symbolic map name. :type mapsize: int :arg mapsize: Specifies the size of the map being defined. - :type values: :class:`Buffer` object. Depends on function prototype. + :type values: :class:`bgl.Buffer` object. Depends on function prototype. :arg values: Specifies an array of mapsize values. @@ -1266,7 +1266,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. .. seealso:: `OpenGL Docs `_ - :type mask: :class:`Buffer` object I{type GL_BYTE} + :type mask: :class:`bgl.Buffer` object I{type GL_BYTE} :arg mask: Specifies a pointer to a 32x32 stipple pattern that will be unpacked from memory in the same way that glDrawPixels unpacks pixels. @@ -1307,9 +1307,9 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type n: int :arg n: Specifies the number of textures to be prioritized. - :type textures: :class:`Buffer` I{type GL_INT} + :type textures: :class:`bgl.Buffer` I{type GL_INT} :arg textures: Specifies an array containing the names of the textures to be prioritized. - :type priorities: :class:`Buffer` I{type GL_FLOAT} + :type priorities: :class:`bgl.Buffer` I{type GL_FLOAT} :arg priorities: Specifies an array containing the texture priorities. A priority given in an element of priorities applies to the texture named by the corresponding element of textures. @@ -1417,7 +1417,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg format: Specifies the format of the pixel data. :type type: Enumerated constant :arg type: Specifies the data type of the pixel data. - :type pixels: :class:`Buffer` object + :type pixels: :class:`bgl.Buffer` object :arg pixels: Returns the pixel data. @@ -1496,7 +1496,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type size: int :arg size: Specifies the size of buffer - :type buffer: :class:`Buffer` I{type GL_INT} + :type buffer: :class:`bgl.Buffer` I{type GL_INT} :arg buffer: Returns the selection data @@ -1575,7 +1575,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type s, t, r, q: Depends on function prototype. (r and q for '3' and '4' prototypes only) :arg s, t, r, q: Specify s, t, r, and q texture coordinates. Not all parameters are present in all forms of the command. - :type v: :class:`Buffer` object. Depends on function prototype. (for 'v' prototypes only) + :type v: :class:`bgl.Buffer` object. Depends on function prototype. (for 'v' prototypes only) :arg v: Specifies a pointer to an array of one, two, three, or four elements, which in turn specify the s, t, r, and q texture coordinates. @@ -1642,7 +1642,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg format: Specifies the format of the pixel data. :type type: Enumerated constant :arg type: Specifies the data type of the pixel data. - :type pixels: :class:`Buffer` object. + :type pixels: :class:`bgl.Buffer` object. :arg pixels: Specifies a pointer to the image data in memory. @@ -1673,7 +1673,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg format: Specifies the format of the pixel data. :type type: Enumerated constant :arg type: Specifies the data type of the pixel data. - :type pixels: :class:`Buffer` object. + :type pixels: :class:`bgl.Buffer` object. :arg pixels: Specifies a pointer to the image data in memory. @@ -1720,7 +1720,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type x, y, z, w: Depends on function prototype (z and w for '3' and '4' prototypes only) :arg x, y, z, w: Specify x, y, z, and w coordinates of a vertex. Not all parameters are present in all forms of the command. - :type v: :class:`Buffer` object. Depends of function prototype (for 'v' + :type v: :class:`bgl.Buffer` object. Depends of function prototype (for 'v' prototypes only) :arg v: Specifies a pointer to an array of two, three, or four elements. The elements of a two-element array are x and y; of a three-element array, @@ -1795,7 +1795,7 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :arg x, y: Specify the center of a picking region in window coordinates. :type width, height: double :arg width, height: Specify the width and height, respectively, of the picking region in window coordinates. - :type viewport: :class:`Buffer` object. [int] + :type viewport: :class:`bgl.Buffer` object. [int] :arg viewport: Specifies the current viewport. @@ -1807,13 +1807,13 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type objx, objy, objz: double :arg objx, objy, objz: Specify the object coordinates. - :type modelMatrix: :class:`Buffer` object. [double] + :type modelMatrix: :class:`bgl.Buffer` object. [double] :arg modelMatrix: Specifies the current modelview matrix (as from a glGetDoublev call). - :type projMatrix: :class:`Buffer` object. [double] + :type projMatrix: :class:`bgl.Buffer` object. [double] :arg projMatrix: Specifies the current projection matrix (as from a glGetDoublev call). - :type viewport: :class:`Buffer` object. [int] + :type viewport: :class:`bgl.Buffer` object. [int] :arg viewport: Specifies the current viewport (as from a glGetIntegerv call). - :type winx, winy, winz: :class:`Buffer` object. [double] + :type winx, winy, winz: :class:`bgl.Buffer` object. [double] :arg winx, winy, winz: Return the computed window coordinates. @@ -1825,13 +1825,13 @@ OpenGL}" and the online NeHe tutorials are two of the best resources. :type winx, winy, winz: double :arg winx, winy, winz: Specify the window coordinates to be mapped. - :type modelMatrix: :class:`Buffer` object. [double] + :type modelMatrix: :class:`bgl.Buffer` object. [double] :arg modelMatrix: Specifies the current modelview matrix (as from a glGetDoublev call). - :type projMatrix: :class:`Buffer` object. [double] + :type projMatrix: :class:`bgl.Buffer` object. [double] :arg projMatrix: Specifies the current projection matrix (as from a glGetDoublev call). - :type viewport: :class:`Buffer` object. [int] + :type viewport: :class:`bgl.Buffer` object. [int] :arg viewport: Specifies the current viewport (as from a glGetIntegerv call). - :type objx, objy, objz: :class:`Buffer` object. [double] + :type objx, objy, objz: :class:`bgl.Buffer` object. [double] :arg objx, objy, objz: Return the computed object coordinates. diff --git a/doc/python_api/rst/info_quickstart.rst b/doc/python_api/rst/info_quickstart.rst index e77e9a76d7f..751e5e1ec61 100644 --- a/doc/python_api/rst/info_quickstart.rst +++ b/doc/python_api/rst/info_quickstart.rst @@ -156,7 +156,7 @@ Note that these properties can only be assigned basic Python types. * array of ints/floats -* dictionary (only string keys types on this list) +* dictionary (only string keys are supported, values must be basic types too) These properties are valid outside of Python. They can be animated by curves or used in driver paths. -- cgit v1.2.3 From a41f45946f8bf7b58e2b6bc048bfa30015e4ba2f Mon Sep 17 00:00:00 2001 From: Campbell Barton Date: Tue, 6 Sep 2011 07:08:20 +0000 Subject: fix for error in strinc.c's BLI_strescape --- source/blender/blenlib/intern/string.c | 4 +++- source/blender/makesrna/intern/rna_access.c | 2 +- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/source/blender/blenlib/intern/string.c b/source/blender/blenlib/intern/string.c index c4ed44f0cdb..ae5fa40f3b9 100644 --- a/source/blender/blenlib/intern/string.c +++ b/source/blender/blenlib/intern/string.c @@ -129,7 +129,7 @@ size_t BLI_strescape(char *dst, const char *src, const size_t maxlen) while(len < maxlen) { switch(*src) { case '\0': - break; + goto escape_finish; case '\\': case '"': @@ -154,6 +154,8 @@ size_t BLI_strescape(char *dst, const char *src, const size_t maxlen) len++; } +escape_finish: + *dst= '\0'; return len; diff --git a/source/blender/makesrna/intern/rna_access.c b/source/blender/makesrna/intern/rna_access.c index 936f2e5e40c..e7d0c5cdec2 100644 --- a/source/blender/makesrna/intern/rna_access.c +++ b/source/blender/makesrna/intern/rna_access.c @@ -4407,7 +4407,7 @@ char *RNA_property_as_string(bContext *C, PointerRNA *ptr, PropertyRNA *prop) buf= MEM_mallocN(sizeof(char)*(length+1), "RNA_property_as_string"); buf_esc= MEM_mallocN(sizeof(char)*(length*2+1), "RNA_property_as_string esc"); RNA_property_string_get(ptr, prop, buf); - BLI_strescape(buf_esc, buf, length*2); + BLI_strescape(buf_esc, buf, length*2+1); MEM_freeN(buf); BLI_dynstr_appendf(dynstr, "\"%s\"", buf_esc); MEM_freeN(buf_esc); -- cgit v1.2.3 From c94fe5e2995873536cbdb180652b1aa027e4ef8d Mon Sep 17 00:00:00 2001 From: Sergey Sharybin Date: Tue, 6 Sep 2011 07:59:18 +0000 Subject: Grease pencil: non-blocking sketch sessions - Implement own undo stack for grease pencil, so now there'll be no keymaps conflicts. - Supported redo's during sketch session. - Get rid of flag stored in Globals -- use undo stack to check if grease pencil session is active. --- source/blender/blenkernel/BKE_global.h | 2 +- source/blender/editors/gpencil/CMakeLists.txt | 1 + source/blender/editors/gpencil/drawgpencil.c | 2 +- source/blender/editors/gpencil/gpencil_intern.h | 6 + source/blender/editors/gpencil/gpencil_paint.c | 136 ++++++++++--------- source/blender/editors/gpencil/gpencil_undo.c | 168 ++++++++++++++++++++++++ source/blender/editors/include/ED_gpencil.h | 4 + source/blender/editors/util/undo.c | 6 + 8 files changed, 263 insertions(+), 62 deletions(-) create mode 100644 source/blender/editors/gpencil/gpencil_undo.c diff --git a/source/blender/blenkernel/BKE_global.h b/source/blender/blenkernel/BKE_global.h index 17876c6ec9d..0e48673f1b1 100644 --- a/source/blender/blenkernel/BKE_global.h +++ b/source/blender/blenkernel/BKE_global.h @@ -111,7 +111,7 @@ typedef struct Global { #define G_SCRIPT_OVERRIDE_PREF (1 << 14) /* when this flag is set ignore the userprefs */ /* #define G_NOFROZEN (1 << 17) also removed */ -#define G_GREASEPENCIL (1 << 17) +/* #define G_GREASEPENCIL (1 << 17) also removed */ /* #define G_AUTOMATKEYS (1 << 30) also removed */ diff --git a/source/blender/editors/gpencil/CMakeLists.txt b/source/blender/editors/gpencil/CMakeLists.txt index 7a2f196fd6d..b312f397939 100644 --- a/source/blender/editors/gpencil/CMakeLists.txt +++ b/source/blender/editors/gpencil/CMakeLists.txt @@ -42,6 +42,7 @@ set(SRC gpencil_edit.c gpencil_ops.c gpencil_paint.c + gpencil_undo.c gpencil_intern.h ) diff --git a/source/blender/editors/gpencil/drawgpencil.c b/source/blender/editors/gpencil/drawgpencil.c index 440d5ee7c4d..cfa9585868e 100644 --- a/source/blender/editors/gpencil/drawgpencil.c +++ b/source/blender/editors/gpencil/drawgpencil.c @@ -644,7 +644,7 @@ static void gp_draw_data (bGPdata *gpd, int offsx, int offsy, int winx, int winy /* Check if may need to draw the active stroke cache, only if this layer is the active layer * that is being edited. (Stroke buffer is currently stored in gp-data) */ - if ((G.f & G_GREASEPENCIL) && (gpl->flag & GP_LAYER_ACTIVE) && + if (ED_gpencil_session_active() && (gpl->flag & GP_LAYER_ACTIVE) && (gpf->flag & GP_FRAME_PAINT)) { /* Buffer stroke needs to be drawn with a different linestyle to help differentiate them from normal strokes. */ diff --git a/source/blender/editors/gpencil/gpencil_intern.h b/source/blender/editors/gpencil/gpencil_intern.h index c31de8d30a7..db4315a8ca6 100644 --- a/source/blender/editors/gpencil/gpencil_intern.h +++ b/source/blender/editors/gpencil/gpencil_intern.h @@ -37,6 +37,7 @@ /* ***************************************************** */ /* Operator Defines */ +struct bGPdata; struct wmOperatorType; /* drawing ---------- */ @@ -61,6 +62,11 @@ void GPENCIL_OT_active_frame_delete(struct wmOperatorType *ot); void GPENCIL_OT_convert(struct wmOperatorType *ot); +/* undo stack ---------- */ + +void gpencil_undo_init(struct bGPdata *gpd); +void gpencil_undo_push(struct bGPdata *gpd); +void gpencil_undo_finish(void); /******************************************************* */ /* FILTERED ACTION DATA - TYPES ---> XXX DEPRECEATED OLD ANIM SYSTEM CODE! */ diff --git a/source/blender/editors/gpencil/gpencil_paint.c b/source/blender/editors/gpencil/gpencil_paint.c index 04565eab155..df5fa65c980 100644 --- a/source/blender/editors/gpencil/gpencil_paint.c +++ b/source/blender/editors/gpencil/gpencil_paint.c @@ -152,7 +152,7 @@ static int gpencil_draw_poll (bContext *C) /* check if current context can support GPencil data */ if (gpencil_data_get_pointers(C, NULL) != NULL) { /* check if Grease Pencil isn't already running */ - if ((G.f & G_GREASEPENCIL) == 0) + if (ED_gpencil_session_active() == 0) return 1; else CTX_wm_operator_poll_msg_set(C, "Grease Pencil operator is already active"); @@ -893,8 +893,10 @@ static void gp_session_validatebuffer (tGPsdata *p) /* clear memory of buffer (or allocate it if starting a new session) */ if (gpd->sbuffer) memset(gpd->sbuffer, 0, sizeof(tGPspoint)*GP_STROKE_BUFFER_MAX); - else + else { + //printf("\t\tGP - allocate sbuffer\n"); gpd->sbuffer= MEM_callocN(sizeof(tGPspoint)*GP_STROKE_BUFFER_MAX, "gp_session_strokebuffer"); + } /* reset indices */ gpd->sbuffer_size = 0; @@ -1051,8 +1053,11 @@ static tGPsdata *gp_session_initpaint (bContext *C) p->gpd= *gpd_ptr; } - /* set edit flags - so that buffer will get drawn */ - G.f |= G_GREASEPENCIL; + if(ED_gpencil_session_active()==0) { + /* initialize undo stack, + also, existing undo stack would make buffer drawn */ + gpencil_undo_init(p->gpd); + } /* clear out buffer (stored in gp-data), in case something contaminated it */ gp_session_validatebuffer(p); @@ -1078,6 +1083,7 @@ static void gp_session_cleanup (tGPsdata *p) /* free stroke buffer */ if (gpd->sbuffer) { + //printf("\t\tGP - free sbuffer\n"); MEM_freeN(gpd->sbuffer); gpd->sbuffer= NULL; } @@ -1247,7 +1253,8 @@ static void gp_paint_strokeend (tGPsdata *p) static void gp_paint_cleanup (tGPsdata *p) { /* finish off a stroke */ - gp_paint_strokeend(p); + if(p->gpd) + gp_paint_strokeend(p); /* "unlock" frame */ if (p->gpf) @@ -1260,8 +1267,8 @@ static void gpencil_draw_exit (bContext *C, wmOperator *op) { tGPsdata *p= op->customdata; - /* clear edit flags */ - G.f &= ~G_GREASEPENCIL; + /* clear undo stack */ + gpencil_undo_finish(); /* restore cursor to indicate end of drawing */ WM_cursor_restore(CTX_wm_window(C)); @@ -1592,6 +1599,7 @@ static int gpencil_draw_invoke (bContext *C, wmOperator *op, wmEvent *event) //printf("\tGP - hotkey invoked... waiting for click-drag\n"); } + WM_event_add_notifier(C, NC_SCREEN|ND_GPENCIL, NULL); /* add a modal handler for this operator, so that we can then draw continuous strokes */ WM_event_add_modal_handler(C, op); return OPERATOR_RUNNING_MODAL; @@ -1609,16 +1617,60 @@ static int gpencil_area_exists(bContext *C, ScrArea *satest) return 0; } +static tGPsdata *gpencil_stroke_begin(bContext *C, wmOperator *op) +{ + tGPsdata *p= op->customdata; + + /* we must check that we're still within the area that we're set up to work from + * otherwise we could crash (see bug #20586) + */ + if (CTX_wm_area(C) != p->sa) { + printf("\t\t\tGP - wrong area execution abort! \n"); + p->status= GP_STATUS_ERROR; + } + + /* free pointer used by previous stroke */ + if(p) + MEM_freeN(p); + + //printf("\t\tGP - start stroke \n"); + + /* we may need to set up paint env again if we're resuming */ + // XXX: watch it with the paintmode! in future, it'd be nice to allow changing paint-mode when in sketching-sessions + // XXX: with tablet events, we may event want to check for eraser here, for nicer tablet support + + gpencil_draw_init(C, op); + + p= op->customdata; + + if(p->status != GP_STATUS_ERROR) + p->status= GP_STATUS_PAINTING; + + return op->customdata; +} + +static void gpencil_stroke_end(wmOperator *op) +{ + tGPsdata *p= op->customdata; + + gp_paint_cleanup(p); + + gpencil_undo_push(p->gpd); + + gp_session_cleanup(p); + + p->status= GP_STATUS_IDLING; + + p->gpd= NULL; + p->gpl= NULL; + p->gpf= NULL; +} + /* events handling during interactive drawing part of operator */ static int gpencil_draw_modal (bContext *C, wmOperator *op, wmEvent *event) { tGPsdata *p= op->customdata; - //int estate = OPERATOR_PASS_THROUGH; /* default exit state - not handled, so let others have a share of the pie */ - /* currently, grease pencil conflicts with such operators as undo and set object mode - which makes behavior of operator totally unpredictable and crash for some cases. - the only way to solve this proper is to ger rid of pointers to data which can - chage stored in operator custom data (sergey) */ - int estate = OPERATOR_RUNNING_MODAL; + int estate = OPERATOR_PASS_THROUGH; /* default exit state - not handled, so let others have a share of the pie */ // if (event->type == NDOF_MOTION) // return OPERATOR_PASS_THROUGH; @@ -1652,11 +1704,13 @@ static int gpencil_draw_modal (bContext *C, wmOperator *op, wmEvent *event) if (GPENCIL_SKETCH_SESSIONS_ON(p->scene)) { /* end stroke only, and then wait to resume painting soon */ //printf("\t\tGP - end stroke only\n"); - gp_paint_cleanup(p); - p->status= GP_STATUS_IDLING; + gpencil_stroke_end(op); /* we've just entered idling state, so this event was processed (but no others yet) */ estate = OPERATOR_RUNNING_MODAL; + + /* stroke could be smoothed, send notifier to refresh screen */ + ED_region_tag_redraw(p->ar); } else { //printf("\t\tGP - end of stroke + op\n"); @@ -1664,35 +1718,19 @@ static int gpencil_draw_modal (bContext *C, wmOperator *op, wmEvent *event) estate = OPERATOR_FINISHED; } } - else { + else if (event->val == KM_PRESS) { /* not painting, so start stroke (this should be mouse-button down) */ - /* we must check that we're still within the area that we're set up to work from - * otherwise we could crash (see bug #20586) - */ - if (CTX_wm_area(C) != p->sa) { - //printf("\t\t\tGP - wrong area execution abort! \n"); - p->status= GP_STATUS_ERROR; + p= gpencil_stroke_begin(C, op); + + if (p->status == GP_STATUS_ERROR) { estate = OPERATOR_CANCELLED; } - else { - //printf("\t\tGP - start stroke \n"); - p->status= GP_STATUS_PAINTING; - - /* we may need to set up paint env again if we're resuming */ - // XXX: watch it with the paintmode! in future, it'd be nice to allow changing paint-mode when in sketching-sessions - // XXX: with tablet events, we may event want to check for eraser here, for nicer tablet support - gp_paint_initstroke(p, p->paintmode); - - if (p->status == GP_STATUS_ERROR) { - estate = OPERATOR_CANCELLED; - } - } + } else { + p->status = GP_STATUS_IDLING; } } - - /* handle mode-specific events */ if (p->status == GP_STATUS_PAINTING) { /* handle painting mouse-movements? */ @@ -1704,7 +1742,7 @@ static int gpencil_draw_modal (bContext *C, wmOperator *op, wmEvent *event) /* finish painting operation if anything went wrong just now */ if (p->status == GP_STATUS_ERROR) { - //printf("\t\t\t\tGP - add error done! \n"); + printf("\t\t\t\tGP - add error done! \n"); estate = OPERATOR_CANCELLED; } else { @@ -1721,28 +1759,6 @@ static int gpencil_draw_modal (bContext *C, wmOperator *op, wmEvent *event) estate = OPERATOR_RUNNING_MODAL; } } - else if (p->status == GP_STATUS_IDLING) { - /* standard undo/redo shouldn't be allowed to execute or else it causes crashes, so catch it here */ - // FIXME: this is a hardcoded hotkey that can't be changed - // TODO: catch redo as well, but how? - if (event->type == ZKEY && event->val == KM_RELEASE) { - /* oskey = cmd key on macs as they seem to use cmd-z for undo as well? */ - if ((event->ctrl) || (event->oskey)) { - /* just delete last stroke, which will look like undo to the end user */ - //printf("caught attempted undo event... deleting last stroke \n"); - gpencil_frame_delete_laststroke(p->gpl, p->gpf); - /* undoing the last line can free p->gpf - * note, could do this in a bit more of an elegant way then a search but it at least prevents a crash */ - if(BLI_findindex(&p->gpl->frames, p->gpf) == -1) { - p->gpf= NULL; - } - - /* event handled, so force refresh */ - ED_region_tag_redraw(p->ar); /* just active area for now, since doing whole screen is too slow */ - estate = OPERATOR_RUNNING_MODAL; - } - } - } /* gpencil modal operator stores area, which can be removed while using it (like fullscreen) */ if(0==gpencil_area_exists(C, p->sa)) diff --git a/source/blender/editors/gpencil/gpencil_undo.c b/source/blender/editors/gpencil/gpencil_undo.c new file mode 100644 index 00000000000..1154975e3cc --- /dev/null +++ b/source/blender/editors/gpencil/gpencil_undo.c @@ -0,0 +1,168 @@ +/* + * $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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + * The Original Code is Copyright (C) 2011 Blender Foundation. + * All rights reserved. + * + * + * Contributor(s): Blender Foundation, + * Sergey Sharybin + * + * ***** END GPL LICENSE BLOCK ***** + */ + +#include +#include + +#include "MEM_guardedalloc.h" + +#include "DNA_gpencil_types.h" +#include "DNA_listBase.h" +#include "DNA_windowmanager_types.h" + +#include "BKE_context.h" +#include "BKE_gpencil.h" + +#include "BLI_listbase.h" + +#include "ED_gpencil.h" + +#include "WM_api.h" +#include "WM_types.h" + +#include "gpencil_intern.h" + +#define MAXUNDONAME 64 + +typedef struct bGPundonode { + struct bGPundonode *next, *prev; + + char name[MAXUNDONAME]; + struct bGPdata *gpd; +} bGPundonode; + +static ListBase undo_nodes = {NULL, NULL}; +static bGPundonode *cur_node = NULL; + +int ED_gpencil_session_active(void) +{ + return undo_nodes.first != NULL; +} + +int ED_undo_gpencil_step(bContext *C, int step, const char *name) +{ + bGPdata **gpd_ptr= NULL, *new_gpd= NULL; + + gpd_ptr= gpencil_data_get_pointers(C, NULL); + + if(step==1) { /* undo */ + //printf("\t\tGP - undo step\n"); + if(cur_node->prev) { + if(!name || strcmp(cur_node->name, name) == 0) { + cur_node= cur_node->prev; + new_gpd= cur_node->gpd; + } + } + } + else if (step==-1) { + //printf("\t\tGP - redo step\n"); + if(cur_node->next) { + if(!name || strcmp(cur_node->name, name) == 0) { + cur_node= cur_node->next; + new_gpd= cur_node->gpd; + } + } + } + + if(new_gpd) { + if(gpd_ptr) { + if(*gpd_ptr) { + bGPdata *gpd= *gpd_ptr; + bGPDlayer *gpl, *gpld; + + free_gpencil_layers(&gpd->layers); + + /* copy layers */ + gpd->layers.first= gpd->layers.last= NULL; + + for (gpl= new_gpd->layers.first; gpl; gpl= gpl->next) { + /* make a copy of source layer and its data */ + gpld= gpencil_layer_duplicate(gpl); + BLI_addtail(&gpd->layers, gpld); + } + } + } + } + + WM_event_add_notifier(C, NC_SCREEN|ND_GPENCIL|NA_EDITED, NULL); + + return OPERATOR_FINISHED; +} + +void gpencil_undo_init(bGPdata *gpd) +{ + gpencil_undo_push(gpd); +} + +void gpencil_undo_push(bGPdata *gpd) +{ + bGPundonode *undo_node; + + //printf("\t\tGP - undo push\n"); + + if(cur_node) { + /* remove all un-done nodes from stack */ + undo_node= cur_node->next; + + while(undo_node) { + bGPundonode *next_node= undo_node->next; + + free_gpencil_data(undo_node->gpd); + MEM_freeN(undo_node->gpd); + + BLI_freelinkN(&undo_nodes, undo_node); + + undo_node= next_node; + } + } + + /* create new undo node */ + undo_node= MEM_callocN(sizeof(bGPundonode), "gpencil undo node"); + undo_node->gpd= gpencil_data_duplicate(gpd); + + cur_node= undo_node; + + BLI_addtail(&undo_nodes, undo_node); +} + +void gpencil_undo_finish(void) +{ + bGPundonode *undo_node= undo_nodes.first; + + while(undo_node) { + free_gpencil_data(undo_node->gpd); + MEM_freeN(undo_node->gpd); + + undo_node= undo_node->next; + } + + BLI_freelistN(&undo_nodes); + + cur_node= NULL; +} diff --git a/source/blender/editors/include/ED_gpencil.h b/source/blender/editors/include/ED_gpencil.h index 07dcc959e32..bfd16487ae5 100644 --- a/source/blender/editors/include/ED_gpencil.h +++ b/source/blender/editors/include/ED_gpencil.h @@ -106,4 +106,8 @@ void paste_gpdata(void); void snap_gplayer_frames(struct bGPDlayer *gpl, short mode); void mirror_gplayer_frames(struct bGPDlayer *gpl, short mode); +/* ------------ Grease-Pencil Undo System ------------------ */ +int ED_gpencil_session_active(void); +int ED_undo_gpencil_step(struct bContext *C, int step, const char *name); + #endif /* ED_GPENCIL_H */ diff --git a/source/blender/editors/util/undo.c b/source/blender/editors/util/undo.c index a2381a208ef..c1aca61f795 100644 --- a/source/blender/editors/util/undo.c +++ b/source/blender/editors/util/undo.c @@ -54,6 +54,7 @@ #include "ED_armature.h" #include "ED_particle.h" #include "ED_curve.h" +#include "ED_gpencil.h" #include "ED_mball.h" #include "ED_mesh.h" #include "ED_object.h" @@ -126,6 +127,11 @@ static int ed_undo_step(bContext *C, int step, const char *undoname) Object *obact= CTX_data_active_object(C); ScrArea *sa= CTX_wm_area(C); + /* grease pencil can be can be used in plenty of spaces, so check it first */ + if(ED_gpencil_session_active()) { + return ED_undo_gpencil_step(C, step, undoname); + } + if(sa && sa->spacetype==SPACE_IMAGE) { SpaceImage *sima= (SpaceImage *)sa->spacedata.first; -- cgit v1.2.3 From 82f7a5e3a25492eb58a0c0ec1933309c37d17e28 Mon Sep 17 00:00:00 2001 From: Lukas Toenne Date: Tue, 6 Sep 2011 08:28:06 +0000 Subject: Fix for #28517, group nodes losing all links from older files. The reason was that group nodes tried to reconstruct sockets from the template lists, which are empty. Now the verification function checks if there are any sockets in the template lists, which are always empty for group nodes. --- source/blender/nodes/intern/node_socket.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/source/blender/nodes/intern/node_socket.c b/source/blender/nodes/intern/node_socket.c index 3ea34dd094a..aabaf5b86de 100644 --- a/source/blender/nodes/intern/node_socket.c +++ b/source/blender/nodes/intern/node_socket.c @@ -422,7 +422,11 @@ static void verify_socket_template_list(bNodeTree *ntree, bNode *node, int in_ou void node_verify_socket_templates(bNodeTree *ntree, bNode *node) { bNodeType *ntype= node->typeinfo; - if(ntype) { + /* XXX Small trick: don't try to match socket lists when there are no templates. + * This also prevents group node sockets from being removed, without the need to explicitly + * check the node type here. + */ + if(ntype && ((ntype->inputs && ntype->inputs[0].type>=0) || (ntype->outputs && ntype->outputs[0].type>=0))) { verify_socket_template_list(ntree, node, SOCK_IN, &node->inputs, ntype->inputs); verify_socket_template_list(ntree, node, SOCK_OUT, &node->outputs, ntype->outputs); } -- cgit v1.2.3 From 32287bebe82615b8500ef0196b7b780745147835 Mon Sep 17 00:00:00 2001 From: Sergey Sharybin Date: Tue, 6 Sep 2011 08:30:17 +0000 Subject: New grease pencil mode: poly line drawing - It's like sketch mode for lines, but you're specifying line knots by clicking on position you want to add next knot. - View can be navigated between knots creation. - Holding LMB down and sliding mouse will lead to new segment preview so it can be created more accurate. Additional change: fixed GP->Bezier conversion. Last point used to be ignored in this operator. --- .../scripts/startup/bl_ui/space_view3d_toolbar.py | 3 + source/blender/editors/gpencil/gpencil_edit.c | 4 +- source/blender/editors/gpencil/gpencil_intern.h | 1 + source/blender/editors/gpencil/gpencil_ops.c | 3 + source/blender/editors/gpencil/gpencil_paint.c | 130 ++++++++++++++++----- 5 files changed, 112 insertions(+), 29 deletions(-) diff --git a/release/scripts/startup/bl_ui/space_view3d_toolbar.py b/release/scripts/startup/bl_ui/space_view3d_toolbar.py index b71593add96..aa26cb43eed 100644 --- a/release/scripts/startup/bl_ui/space_view3d_toolbar.py +++ b/release/scripts/startup/bl_ui/space_view3d_toolbar.py @@ -54,6 +54,9 @@ def draw_gpencil_tools(context, layout): row = col.row() row.operator("gpencil.draw", text="Draw").mode = 'DRAW' row.operator("gpencil.draw", text="Line").mode = 'DRAW_STRAIGHT' + + row = col.row() + row.operator("gpencil.draw", text="Poly").mode = 'DRAW_POLY' row.operator("gpencil.draw", text="Erase").mode = 'ERASER' row = col.row() diff --git a/source/blender/editors/gpencil/gpencil_edit.c b/source/blender/editors/gpencil/gpencil_edit.c index 9dc764b7aac..1cd8b1f05db 100644 --- a/source/blender/editors/gpencil/gpencil_edit.c +++ b/source/blender/editors/gpencil/gpencil_edit.c @@ -511,8 +511,8 @@ static void gp_stroke_to_bezier (bContext *C, bGPDlayer *gpl, bGPDstroke *gps, C copy_v3_v3(p3d_prev, p3d_cur); copy_v3_v3(p3d_cur, p3d_next); - if (i + 1 < tot) { - gp_strokepoint_convertcoords(C, gps, pt+1, p3d_next, subrect); + if (i + 2 < tot) { + gp_strokepoint_convertcoords(C, gps, pt + 2, p3d_next, subrect); } } diff --git a/source/blender/editors/gpencil/gpencil_intern.h b/source/blender/editors/gpencil/gpencil_intern.h index db4315a8ca6..8000af54f53 100644 --- a/source/blender/editors/gpencil/gpencil_intern.h +++ b/source/blender/editors/gpencil/gpencil_intern.h @@ -49,6 +49,7 @@ typedef enum eGPencil_PaintModes { GP_PAINTMODE_DRAW = 0, GP_PAINTMODE_ERASER, GP_PAINTMODE_DRAW_STRAIGHT, + GP_PAINTMODE_DRAW_POLY } eGPencil_PaintModes; /* buttons editing --- */ diff --git a/source/blender/editors/gpencil/gpencil_ops.c b/source/blender/editors/gpencil/gpencil_ops.c index e1e4c8d5457..150e0ba90e4 100644 --- a/source/blender/editors/gpencil/gpencil_ops.c +++ b/source/blender/editors/gpencil/gpencil_ops.c @@ -59,6 +59,9 @@ void ED_keymap_gpencil(wmKeyConfig *keyconf) /* draw - straight lines */ kmi=WM_keymap_add_item(keymap, "GPENCIL_OT_draw", LEFTMOUSE, KM_PRESS, KM_CTRL, DKEY); RNA_enum_set(kmi->ptr, "mode", GP_PAINTMODE_DRAW_STRAIGHT); + /* draw - poly lines */ + kmi=WM_keymap_add_item(keymap, "GPENCIL_OT_draw", RIGHTMOUSE, KM_PRESS, KM_CTRL, DKEY); + RNA_enum_set(kmi->ptr, "mode", GP_PAINTMODE_DRAW_POLY); /* erase */ kmi=WM_keymap_add_item(keymap, "GPENCIL_OT_draw", RIGHTMOUSE, KM_PRESS, 0, DKEY); RNA_enum_set(kmi->ptr, "mode", GP_PAINTMODE_ERASER); diff --git a/source/blender/editors/gpencil/gpencil_paint.c b/source/blender/editors/gpencil/gpencil_paint.c index df5fa65c980..460408c6269 100644 --- a/source/blender/editors/gpencil/gpencil_paint.c +++ b/source/blender/editors/gpencil/gpencil_paint.c @@ -124,6 +124,7 @@ enum { /* Runtime flags */ enum { GP_PAINTFLAG_FIRSTRUN = (1<<0), /* operator just started */ + GP_PAINTFLAG_STROKEADDED = (1<<1) /* stroke was already added during draw session */ }; /* ------ */ @@ -375,6 +376,43 @@ static short gp_stroke_addpoint (tGPsdata *p, const int mval[2], float pressure) else return GP_STROKEADD_NORMAL; } + else if (p->paintmode == GP_PAINTMODE_DRAW_POLY) { + /* get pointer to destination point */ + pt= (tGPspoint *)(gpd->sbuffer); + + /* store settings */ + pt->x= mval[0]; + pt->y= mval[1]; + pt->pressure= pressure; + + /* if there's stroke fir this poly line session add (or replace last) point + to stroke. This allows to draw lines more interactively (see new segment + during mouse slide, i.e.) */ + if (p->flags & GP_PAINTFLAG_STROKEADDED) { + bGPDstroke *gps= p->gpf->strokes.last; + bGPDspoint *pts; + + /* first time point is adding to temporary buffer -- need to allocate new point in stroke */ + if (gpd->sbuffer_size == 0) { + gps->points = MEM_reallocN(gps->points, sizeof(bGPDspoint)*(gps->totpoints+1)); + gps->totpoints++; + } + + pts = &gps->points[gps->totpoints-1]; + + /* convert screen-coordinates to appropriate coordinates (and store them) */ + gp_stroke_convertcoords(p, &pt->x, &pts->x, NULL); + + /* copy pressure */ + pts->pressure= pt->pressure; + } + + /* increment counters */ + if (gpd->sbuffer_size == 0) + gpd->sbuffer_size++; + + return GP_STROKEADD_NORMAL; + } /* return invalid state for now... */ return GP_STROKEADD_INVALID; @@ -395,7 +433,7 @@ static void gp_stroke_smooth (tGPsdata *p) int i=0, cmx=gpd->sbuffer_size; /* only smooth if smoothing is enabled, and we're not doing a straight line */ - if (!(U.gp_settings & GP_PAINT_DOSMOOTH) || (p->paintmode == GP_PAINTMODE_DRAW_STRAIGHT)) + if (!(U.gp_settings & GP_PAINT_DOSMOOTH) || ELEM(p->paintmode, GP_PAINTMODE_DRAW_STRAIGHT, GP_PAINTMODE_DRAW_POLY)) return; /* don't try if less than 2 points in buffer */ @@ -527,17 +565,28 @@ static void gp_stroke_newfrombuffer (tGPsdata *p) return; } + /* special case for poly line -- for already added stroke during session + coordinates are getting added to stroke immediatelly to allow more + interactive behavior */ + if (p->paintmode == GP_PAINTMODE_DRAW_POLY) { + if (p->flags & GP_PAINTFLAG_STROKEADDED) + return; + } + /* allocate memory for a new stroke */ gps= MEM_callocN(sizeof(bGPDstroke), "gp_stroke"); - /* allocate enough memory for a continuous array for storage points */ - pt= gps->points= MEM_callocN(sizeof(bGPDspoint)*totelem, "gp_stroke_points"); - /* copy appropriate settings for stroke */ gps->totpoints= totelem; gps->thickness= p->gpl->thickness; gps->flag= gpd->sbuffer_sflag; + /* allocate enough memory for a continuous array for storage points */ + gps->points= MEM_callocN(sizeof(bGPDspoint)*gps->totpoints, "gp_stroke_points"); + + /* set pointer to first non-initialized point */ + pt= gps->points + (gps->totpoints - totelem); + /* copy points from the buffer to the stroke */ if (p->paintmode == GP_PAINTMODE_DRAW_STRAIGHT) { /* straight lines only -> only endpoints */ @@ -565,6 +614,16 @@ static void gp_stroke_newfrombuffer (tGPsdata *p) pt->pressure= ptc->pressure; } } + else if (p->paintmode == GP_PAINTMODE_DRAW_POLY) { + /* first point */ + ptc= gpd->sbuffer; + + /* convert screen-coordinates to appropriate coordinates (and store them) */ + gp_stroke_convertcoords(p, &ptc->x, &pt->x, NULL); + + /* copy pressure */ + pt->pressure= ptc->pressure; + } else { float *depth_arr= NULL; @@ -643,6 +702,8 @@ static void gp_stroke_newfrombuffer (tGPsdata *p) MEM_freeN(depth_arr); } + p->flags |= GP_PAINTFLAG_STROKEADDED; + /* add stroke to frame */ BLI_addtail(&p->gpf->strokes, gps); } @@ -891,8 +952,10 @@ static void gp_session_validatebuffer (tGPsdata *p) bGPdata *gpd= p->gpd; /* clear memory of buffer (or allocate it if starting a new session) */ - if (gpd->sbuffer) + if (gpd->sbuffer) { + //printf("\t\tGP - reset sbuffer\n"); memset(gpd->sbuffer, 0, sizeof(tGPspoint)*GP_STROKE_BUFFER_MAX); + } else { //printf("\t\tGP - allocate sbuffer\n"); gpd->sbuffer= MEM_callocN(sizeof(tGPspoint)*GP_STROKE_BUFFER_MAX, "gp_session_strokebuffer"); @@ -905,24 +968,21 @@ static void gp_session_validatebuffer (tGPsdata *p) gpd->sbuffer_sflag= 0; } -/* init new painting session */ -static tGPsdata *gp_session_initpaint (bContext *C) +/* (re)init new painting data */ +static int gp_session_initdata (bContext *C, tGPsdata *p) { - tGPsdata *p = NULL; bGPdata **gpd_ptr = NULL; ScrArea *curarea= CTX_wm_area(C); ARegion *ar= CTX_wm_region(C); /* make sure the active view (at the starting time) is a 3d-view */ if (curarea == NULL) { + p->status= GP_STATUS_ERROR; if (G.f & G_DEBUG) printf("Error: No active view for painting \n"); - return NULL; + return 0; } - /* create new context data */ - p= MEM_callocN(sizeof(tGPsdata), "GPencil Drawing Data"); - /* pass on current scene and window */ p->scene= CTX_data_scene(C); p->win= CTX_wm_window(C); @@ -944,7 +1004,7 @@ static tGPsdata *gp_session_initpaint (bContext *C) p->status= GP_STATUS_ERROR; if (G.f & G_DEBUG) printf("Error: 3D-View active region doesn't have any region data, so cannot be drawable \n"); - return p; + return 0; } #if 0 // XXX will this sort of antiquated stuff be restored? @@ -953,7 +1013,7 @@ static tGPsdata *gp_session_initpaint (bContext *C) p->status= GP_STATUS_ERROR; if (G.f & G_DEBUG) printf("Error: In active view, Grease Pencil not shown \n"); - return p; + return 0; } #endif } @@ -974,7 +1034,7 @@ static tGPsdata *gp_session_initpaint (bContext *C) p->status= GP_STATUS_ERROR; if (G.f & G_DEBUG) printf("Error: In active view, Grease Pencil not shown \n"); - return; + return 0; } #endif } @@ -994,13 +1054,13 @@ static tGPsdata *gp_session_initpaint (bContext *C) p->status= GP_STATUS_ERROR; if (G.f & G_DEBUG) printf("Error: In active view (sequencer), active mode doesn't support Grease Pencil \n"); - return; + return 0; } if ((sseq->flag & SEQ_DRAW_GPENCIL)==0) { p->status= GP_STATUS_ERROR; if (G.f & G_DEBUG) printf("Error: In active view, Grease Pencil not shown \n"); - return; + return 0; } } break; @@ -1021,7 +1081,7 @@ static tGPsdata *gp_session_initpaint (bContext *C) p->status= GP_STATUS_ERROR; if (G.f & G_DEBUG) printf("Error: In active view, Grease Pencil not shown \n"); - return p; + return 0; } #endif } @@ -1033,7 +1093,7 @@ static tGPsdata *gp_session_initpaint (bContext *C) p->status= GP_STATUS_ERROR; if (G.f & G_DEBUG) printf("Error: Active view not appropriate for Grease Pencil drawing \n"); - return p; + return 0; } break; } @@ -1044,7 +1104,7 @@ static tGPsdata *gp_session_initpaint (bContext *C) p->status= GP_STATUS_ERROR; if (G.f & G_DEBUG) printf("Error: Current context doesn't allow for any Grease Pencil data \n"); - return p; + return 0; } else { /* if no existing GPencil block exists, add one */ @@ -1067,6 +1127,19 @@ static tGPsdata *gp_session_initpaint (bContext *C) p->im2d_settings.sizex= 1; p->im2d_settings.sizey= 1; #endif + + return 1; +} + +/* init new painting session */ +static tGPsdata *gp_session_initpaint (bContext *C) +{ + tGPsdata *p = NULL; + + /* create new context data */ + p= MEM_callocN(sizeof(tGPsdata), "GPencil Drawing Data"); + + gp_session_initdata(C, p); /* return context data for running paint operator */ return p; @@ -1629,17 +1702,14 @@ static tGPsdata *gpencil_stroke_begin(bContext *C, wmOperator *op) p->status= GP_STATUS_ERROR; } - /* free pointer used by previous stroke */ - if(p) - MEM_freeN(p); - //printf("\t\tGP - start stroke \n"); /* we may need to set up paint env again if we're resuming */ // XXX: watch it with the paintmode! in future, it'd be nice to allow changing paint-mode when in sketching-sessions // XXX: with tablet events, we may event want to check for eraser here, for nicer tablet support - gpencil_draw_init(C, op); + if (gp_session_initdata(C, p)) + gp_paint_initstroke(p, p->paintmode); p= op->customdata; @@ -1698,10 +1768,15 @@ static int gpencil_draw_modal (bContext *C, wmOperator *op, wmEvent *event) if (ELEM(event->type, LEFTMOUSE, RIGHTMOUSE)) { /* if painting, end stroke */ if (p->status == GP_STATUS_PAINTING) { + int sketch= 0; /* basically, this should be mouse-button up = end stroke * BUT what happens next depends on whether we 'painting sessions' is enabled */ - if (GPENCIL_SKETCH_SESSIONS_ON(p->scene)) { + sketch|= GPENCIL_SKETCH_SESSIONS_ON(p->scene); + /* polyline drawig is also 'sketching' -- all knots should be added during one session */ + sketch|= p->paintmode == GP_PAINTMODE_DRAW_POLY; + + if (sketch) { /* end stroke only, and then wait to resume painting soon */ //printf("\t\tGP - end stroke only\n"); gpencil_stroke_end(op); @@ -1710,7 +1785,7 @@ static int gpencil_draw_modal (bContext *C, wmOperator *op, wmEvent *event) estate = OPERATOR_RUNNING_MODAL; /* stroke could be smoothed, send notifier to refresh screen */ - ED_region_tag_redraw(p->ar); + WM_event_add_notifier(C, NC_SCREEN|ND_GPENCIL|NA_EDITED, NULL); } else { //printf("\t\tGP - end of stroke + op\n"); @@ -1794,6 +1869,7 @@ static int gpencil_draw_modal (bContext *C, wmOperator *op, wmEvent *event) static EnumPropertyItem prop_gpencil_drawmodes[] = { {GP_PAINTMODE_DRAW, "DRAW", 0, "Draw Freehand", ""}, {GP_PAINTMODE_DRAW_STRAIGHT, "DRAW_STRAIGHT", 0, "Draw Straight Lines", ""}, + {GP_PAINTMODE_DRAW_POLY, "DRAW_POLY", 0, "Dtaw Poly Line", ""}, {GP_PAINTMODE_ERASER, "ERASER", 0, "Eraser", ""}, {0, NULL, 0, NULL, NULL} }; -- cgit v1.2.3 From 7062788017cfb2841596d15f7c37612312692195 Mon Sep 17 00:00:00 2001 From: Campbell Barton Date: Tue, 6 Sep 2011 10:49:55 +0000 Subject: texture evaluation function (like we had in 2.4x api), requested by Lee. eg: red, green, blue, intensity = texture.evaluate(vec) --- source/blender/makesrna/intern/rna_internal.h | 1 + source/blender/makesrna/intern/rna_texture.c | 2 + source/blender/makesrna/intern/rna_texture_api.c | 54 ++++++++++++++++++------ 3 files changed, 45 insertions(+), 12 deletions(-) diff --git a/source/blender/makesrna/intern/rna_internal.h b/source/blender/makesrna/intern/rna_internal.h index 9e98f166875..78b8c67d92c 100644 --- a/source/blender/makesrna/intern/rna_internal.h +++ b/source/blender/makesrna/intern/rna_internal.h @@ -261,6 +261,7 @@ void RNA_api_wm(struct StructRNA *srna); void RNA_api_sensor(struct StructRNA *srna); void RNA_api_controller(struct StructRNA *srna); void RNA_api_actuator(struct StructRNA *srna); +void RNA_api_texture(struct StructRNA *srna); void RNA_api_environment_map(struct StructRNA *srna); /* main collection functions */ diff --git a/source/blender/makesrna/intern/rna_texture.c b/source/blender/makesrna/intern/rna_texture.c index 503212201c4..890be76c49a 100644 --- a/source/blender/makesrna/intern/rna_texture.c +++ b/source/blender/makesrna/intern/rna_texture.c @@ -1820,6 +1820,8 @@ static void rna_def_texture(BlenderRNA *brna) rna_def_texture_pointdensity(brna); rna_def_texture_voxeldata(brna); /* XXX add more types here .. */ + + RNA_api_texture(srna); } void RNA_def_texture(BlenderRNA *brna) diff --git a/source/blender/makesrna/intern/rna_texture_api.c b/source/blender/makesrna/intern/rna_texture_api.c index 8d4b73f1f0c..8c63d5da8fd 100644 --- a/source/blender/makesrna/intern/rna_texture_api.c +++ b/source/blender/makesrna/intern/rna_texture_api.c @@ -43,6 +43,7 @@ #include "BKE_context.h" #include "BKE_global.h" #include "RE_pipeline.h" +#include "RE_shader_ext.h" void save_envmap(struct EnvMap *env, bContext *C, ReportList *reports, const char* filepath, struct Scene *scene, float layout[12]) { @@ -67,30 +68,59 @@ void clear_envmap(struct EnvMap *env, bContext *C) } } +void texture_evaluate(struct Tex *tex, float value[3], float color_r[3]) +{ + TexResult texres= {0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0, NULL}; + multitex_ext(tex, value, NULL, NULL, 1, &texres); + + color_r[0] = texres.tr; + color_r[1] = texres.tg; + color_r[2] = texres.tb; + color_r[3] = texres.tin; +} + #else +void RNA_api_texture(StructRNA *srna) +{ + FunctionRNA *func; + PropertyRNA *parm; + + func= RNA_def_function(srna, "evaluate", "texture_evaluate"); + RNA_def_function_ui_description(func, "Evaluate the texture at the coordinates given"); + + parm= RNA_def_float_vector(func, "value", 3, NULL, -FLT_MAX, FLT_MAX, "", "", -1e4, 1e4); + RNA_def_property_flag(parm, PROP_REQUIRED); + + /* return location and normal */ + parm= RNA_def_float_vector(func, "result", 4, NULL, -FLT_MAX, FLT_MAX, "Result", NULL, -1e4, 1e4); + RNA_def_property_flag(parm, PROP_THICK_WRAP); + RNA_def_function_output(func, parm); + +} + void RNA_api_environment_map(StructRNA *srna) { FunctionRNA *func; PropertyRNA *parm; - + static const float default_layout[] = { 0,0, 1,0, 2,0, 0,1, 1,1, 2,1 }; - + func= RNA_def_function(srna, "clear", "clear_envmap"); - RNA_def_function_ui_description(func, "Discard the environment map and free it from memory."); - RNA_def_function_flag(func, FUNC_USE_CONTEXT); + RNA_def_function_ui_description(func, "Discard the environment map and free it from memory."); + RNA_def_function_flag(func, FUNC_USE_CONTEXT); func= RNA_def_function(srna,"save", "save_envmap"); - RNA_def_function_ui_description(func, "Save the environment map to disc using the scene render settings."); - RNA_def_function_flag(func, FUNC_USE_CONTEXT|FUNC_USE_REPORTS); - - parm= RNA_def_string_file_name(func,"filepath","",FILE_MAX,"File path","Location of the output file"); - RNA_def_property_flag(parm, PROP_REQUIRED); - - RNA_def_pointer(func, "scene", "Scene", "", "Overrides the scene from which image parameters are taken."); + RNA_def_function_ui_description(func, "Save the environment map to disc using the scene render settings."); + RNA_def_function_flag(func, FUNC_USE_CONTEXT|FUNC_USE_REPORTS); + + parm= RNA_def_string_file_name(func,"filepath","",FILE_MAX,"File path","Location of the output file"); + RNA_def_property_flag(parm, PROP_REQUIRED); + + RNA_def_pointer(func, "scene", "Scene", "", "Overrides the scene from which image parameters are taken."); - parm = RNA_def_float_array(func, "layout", 12, default_layout, 0.0f, 0.0f, "File layout", "Flat array describing the X,Y position of each cube face in the output image, where 1 is the size of a face. Order is [+Z -Z +Y -X -Y +X]. Use -1 to skip a face.", 0.0f, 0.0f); + parm = RNA_def_float_array(func, "layout", 12, default_layout, 0.0f, 0.0f, "File layout", "Flat array describing the X,Y position of each cube face in the output image, where 1 is the size of a face. Order is [+Z -Z +Y -X -Y +X]. Use -1 to skip a face.", 0.0f, 0.0f); } #endif -- cgit v1.2.3 From aabd702dbdbba5af116f37c401f6a17f0ac714ca Mon Sep 17 00:00:00 2001 From: Antony Riakiotakis Date: Tue, 6 Sep 2011 11:17:29 +0000 Subject: fix link issues with MinGW - a substitute declaration(correctByteOrder) for itoln that was not present in MinGW was being used. Duplicated the declaration from (tried including but gave some errors) and added the appropriate link library, wsock32, according to MinGW documentation. --- CMakeLists.txt | 2 +- build_files/scons/config/win32-mingw-config.py | 2 +- intern/guardedalloc/MEM_sys_types.h | 5 ++++- source/blender/blenloader/BLO_sys_types.h | 9 ++++++++- 4 files changed, 14 insertions(+), 4 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index b54b18aab37..8b5693fb1aa 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -797,7 +797,7 @@ elseif(WIN32) else() # keep GCC spesific stuff here if(CMAKE_COMPILER_IS_GNUCC) - set(PLATFORM_LINKLIBS "-lshell32 -lshfolder -lgdi32 -lmsvcrt -lwinmm -lmingw32 -lm -lws2_32 -lz -lstdc++ -lole32 -luuid") + set(PLATFORM_LINKLIBS "-lshell32 -lshfolder -lgdi32 -lmsvcrt -lwinmm -lmingw32 -lm -lws2_32 -lz -lstdc++ -lole32 -luuid -lwsock32") set(PLATFORM_CFLAGS "-pipe -funsigned-char -fno-strict-aliasing") add_definitions(-D_LARGEFILE_SOURCE -D_FILE_OFFSET_BITS=64 -D_LARGEFILE64_SOURCE) diff --git a/build_files/scons/config/win32-mingw-config.py b/build_files/scons/config/win32-mingw-config.py index c815b76ef73..37d693db560 100644 --- a/build_files/scons/config/win32-mingw-config.py +++ b/build_files/scons/config/win32-mingw-config.py @@ -174,7 +174,7 @@ C_WARN = ['-Wno-char-subscripts', '-Wdeclaration-after-statement', '-Wstrict-pro CC_WARN = [ '-Wall' ] -LLIBS = ['-lshell32', '-lshfolder', '-lgdi32', '-lmsvcrt', '-lwinmm', '-lmingw32', '-lm', '-lws2_32', '-lz', '-lstdc++','-lole32','-luuid'] +LLIBS = ['-lshell32', '-lshfolder', '-lgdi32', '-lmsvcrt', '-lwinmm', '-lmingw32', '-lm', '-lws2_32', '-lz', '-lstdc++','-lole32','-luuid', '-lwsock32'] PLATFORM_LINKFLAGS = ['--stack,2097152'] diff --git a/intern/guardedalloc/MEM_sys_types.h b/intern/guardedalloc/MEM_sys_types.h index 48230db23a3..4debb32b5c4 100644 --- a/intern/guardedalloc/MEM_sys_types.h +++ b/intern/guardedalloc/MEM_sys_types.h @@ -98,7 +98,8 @@ typedef unsigned long uintptr_t; #include #elif defined(FREE_WINDOWS) - +/* define htoln here, there must be a syntax error in winsock2.h in MinGW */ +unsigned long __attribute__((__stdcall__)) htonl(unsigned long); #include #else @@ -109,12 +110,14 @@ typedef unsigned long uintptr_t; #endif /* ifdef platform for types */ #ifdef _WIN32 +#ifndef FREE_WINDOWS #ifndef htonl #define htonl(x) correctByteOrder(x) #endif #ifndef ntohl #define ntohl(x) correctByteOrder(x) #endif +#endif #elif defined (__FreeBSD__) || defined (__OpenBSD__) #include #elif defined (__APPLE__) diff --git a/source/blender/blenloader/BLO_sys_types.h b/source/blender/blenloader/BLO_sys_types.h index 2114fc34bf1..4b3902dca43 100644 --- a/source/blender/blenloader/BLO_sys_types.h +++ b/source/blender/blenloader/BLO_sys_types.h @@ -93,7 +93,8 @@ typedef unsigned long uintptr_t; #include #elif defined(FREE_WINDOWS) - +/* define htoln here, there must be a syntax error in winsock2.h in MinGW */ +unsigned long __attribute__((__stdcall__)) htonl(unsigned long); #include #else @@ -105,8 +106,14 @@ typedef unsigned long uintptr_t; #ifdef _WIN32 +#ifndef FREE_WINDOWS +#ifndef htonl #define htonl(x) correctByteOrder(x) +#endif +#ifndef ntohl #define ntohl(x) correctByteOrder(x) +#endif +#endif #elif defined (__FreeBSD__) || defined (__OpenBSD__) #include #elif defined (__APPLE__) -- cgit v1.2.3 From c6002873fa5b967ce30b9fc827fb6abc0931ef3c Mon Sep 17 00:00:00 2001 From: Lukas Toenne Date: Tue, 6 Sep 2011 11:38:44 +0000 Subject: Backward compatibility fix for SOCK_DYNAMICS flag on group sockets. This is currently only needed for displaying the up/down buttons of group sockets. All regular group sockets should have this flag to indicate they are added by the user. More complex "group-type" trees may use non-dynamic sockets in the future for sockets that are not supposed to be manipulated. --- source/blender/blenloader/intern/readfile.c | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c index 355fc14705a..66e38f1c5f8 100644 --- a/source/blender/blenloader/intern/readfile.c +++ b/source/blender/blenloader/intern/readfile.c @@ -7015,6 +7015,15 @@ static void do_versions_nodetree_default_value(bNodeTree *ntree) do_versions_socket_default_value(sock); } +static void do_versions_nodetree_dynamic_sockets(bNodeTree *ntree) +{ + bNodeSocket *sock; + for (sock=ntree->inputs.first; sock; sock=sock->next) + sock->flag |= SOCK_DYNAMIC; + for (sock=ntree->outputs.first; sock; sock=sock->next) + sock->flag |= SOCK_DYNAMIC; +} + static void do_versions(FileData *fd, Library *lib, Main *main) { /* WATCH IT!!!: pointers from libdata have not been converted */ @@ -11972,6 +11981,16 @@ static void do_versions(FileData *fd, Library *lib, Main *main) tex->nodetree->update |= NTREE_UPDATE; } } + + /* add SOCK_DYNAMIC flag to existing group sockets */ + { + bNodeTree *ntree; + /* only need to do this for trees in main, local trees are not used as groups */ + for (ntree=main->nodetree.first; ntree; ntree=ntree->id.next) { + do_versions_nodetree_dynamic_sockets(ntree); + ntree->update |= NTREE_UPDATE; + } + } } /* put compatibility code here until next subversion bump */ -- cgit v1.2.3 From 71abf218f0dcc8e2b038de3672a8332fd3e544af Mon Sep 17 00:00:00 2001 From: Lukas Toenne Date: Tue, 6 Sep 2011 11:42:20 +0000 Subject: Fix for wrong offset of the input socket column in group node tree display. --- source/blender/editors/space_node/drawnode.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/blender/editors/space_node/drawnode.c b/source/blender/editors/space_node/drawnode.c index 890b04dce91..0d2ec7c646f 100644 --- a/source/blender/editors/space_node/drawnode.c +++ b/source/blender/editors/space_node/drawnode.c @@ -637,7 +637,7 @@ static void draw_group_socket(const bContext *C, SpaceNode *snode, bNodeTree *nt float arrowbutw= 0.8f*UI_UNIT_X; /* layout stuff for buttons on group left frame */ float colw= 0.6f*node_group_frame; - float col1= 6; + float col1= 6 - node_group_frame; float col2= col1 + colw+6; float col3= node_group_frame - arrowbutw - 6; /* layout stuff for buttons on group right frame */ -- cgit v1.2.3 From 47ffe63c86eb495aa5556939467692484aea8322 Mon Sep 17 00:00:00 2001 From: Campbell Barton Date: Tue, 6 Sep 2011 13:00:46 +0000 Subject: remove -Wundef for code we don't maintain & generated code. --- build_files/cmake/macros.cmake | 1 + 1 file changed, 1 insertion(+) diff --git a/build_files/cmake/macros.cmake b/build_files/cmake/macros.cmake index 58938c8b0b0..d09215d040d 100644 --- a/build_files/cmake/macros.cmake +++ b/build_files/cmake/macros.cmake @@ -392,6 +392,7 @@ macro(remove_strict_flags) remove_flag("-Wstrict-prototypes") remove_flag("-Wunused-parameter") remove_flag("-Wwrite-strings") + remove_flag("-Wundef") remove_flag("-Wshadow") remove_flag("-Werror=[^ ]+") remove_flag("-Werror") -- cgit v1.2.3 From 0c15f834e49b2e1c43c0e06f1fd8a7e7f5faa83f Mon Sep 17 00:00:00 2001 From: Sergey Sharybin Date: Tue, 6 Sep 2011 14:02:28 +0000 Subject: Fix for poly line grease pencil and surface drawing. --- source/blender/editors/gpencil/gpencil_paint.c | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/source/blender/editors/gpencil/gpencil_paint.c b/source/blender/editors/gpencil/gpencil_paint.c index 460408c6269..a23f2064a9e 100644 --- a/source/blender/editors/gpencil/gpencil_paint.c +++ b/source/blender/editors/gpencil/gpencil_paint.c @@ -400,6 +400,15 @@ static short gp_stroke_addpoint (tGPsdata *p, const int mval[2], float pressure) pts = &gps->points[gps->totpoints-1]; + /* special case for poly lines: normally, depth is needed only when creating new stroke from buffer, + but poly lines are converting to stroke instantly, so initialize depth buffer before converting coordinates */ + if (gpencil_project_check(p)) { + View3D *v3d= p->sa->spacedata.first; + + view3d_region_operator_needs_opengl(p->win, p->ar); + ED_view3d_autodist_init(p->scene, p->ar, v3d, (p->gpd->flag & GP_DATA_DEPTH_STROKE) ? 1:0); + } + /* convert screen-coordinates to appropriate coordinates (and store them) */ gp_stroke_convertcoords(p, &pt->x, &pts->x, NULL); -- cgit v1.2.3 From d4ce95d1dc9103c018b17f42872d231cece33383 Mon Sep 17 00:00:00 2001 From: Sergey Sharybin Date: Tue, 6 Sep 2011 14:59:55 +0000 Subject: Fix #28524: Push/Pull Assert when using Operator Panel to Alter Distance value Some transform operators (like push/pull, shrink/fatten, to sphere and so) were creating "value" as single scalar value. This used to confuse RNA_float_get_array used in initTransform. Use RNA_float_get_array for array values and RNA_float_get for scalar value in transform initi function. --- source/blender/editors/transform/transform.c | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/source/blender/editors/transform/transform.c b/source/blender/editors/transform/transform.c index 09507194969..1796bd4e928 100644 --- a/source/blender/editors/transform/transform.c +++ b/source/blender/editors/transform/transform.c @@ -1678,7 +1678,14 @@ int initTransform(bContext *C, TransInfo *t, wmOperator *op, wmEvent *event, int if (RNA_property_is_set(op->ptr, "value")) { float values[4]= {0}; /* incase value isn't length 4, avoid uninitialized memory */ - RNA_float_get_array(op->ptr, "value", values); + PropertyRNA *prop= RNA_struct_find_property(op->ptr, "value"); + + if(RNA_property_array_check(prop)) { + RNA_float_get_array(op->ptr, "value", values); + } else { + values[0]= RNA_float_get(op->ptr, "value"); + } + QUATCOPY(t->values, values); QUATCOPY(t->auto_values, values); t->flag |= T_AUTOVALUES; -- cgit v1.2.3 From e79d16270bc29f44431689fdb1b362b1866ab8c3 Mon Sep 17 00:00:00 2001 From: Thomas Dinges Date: Tue, 6 Sep 2011 15:44:44 +0000 Subject: Ambient Occlusion: * Increase max. samples from 32 to 128. --- source/blender/makesrna/intern/rna_world.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/blender/makesrna/intern/rna_world.c b/source/blender/makesrna/intern/rna_world.c index 72b54dce473..11ec327c306 100644 --- a/source/blender/makesrna/intern/rna_world.c +++ b/source/blender/makesrna/intern/rna_world.c @@ -360,7 +360,7 @@ static void rna_def_lighting(BlenderRNA *brna) prop= RNA_def_property(srna, "samples", PROP_INT, PROP_NONE); RNA_def_property_int_sdna(prop, NULL, "aosamp"); - RNA_def_property_range(prop, 1, 32); + RNA_def_property_range(prop, 1, 128); RNA_def_property_ui_text(prop, "Samples", "Amount of ray samples. Higher values give smoother results and longer rendering times"); RNA_def_property_update(prop, 0, "rna_World_update"); -- cgit v1.2.3 From 884fc84793be1c5fdd6643ad267331381f8e1c6b Mon Sep 17 00:00:00 2001 From: Lukas Toenne Date: Tue, 6 Sep 2011 16:32:51 +0000 Subject: Fix for multiple parallel group node executions. This would previously break because begin/end functions for each tree type still have some checks of the ntree->execdata pointer in them, despite the intended use of execdata instances instead of trees themselves for execution data storage. This is an artifact of the old execution system that required these checks to be made in the functions to avoid multiple execution of top-level trees. Now these functions take an additional argument, so group nodes can prevent them from setting and checking the nodetree->execdata pointers. --- source/blender/blenkernel/BKE_node.h | 12 +++--- source/blender/blenkernel/intern/material.c | 4 +- source/blender/blenkernel/intern/node.c | 6 +-- source/blender/blenkernel/intern/texture.c | 2 +- source/blender/editors/sculpt_paint/paint_image.c | 4 +- source/blender/editors/sculpt_paint/sculpt.c | 4 +- .../blender/nodes/composite/node_composite_tree.c | 47 ++++++++++++++-------- .../nodes/composite/nodes/node_composite_common.c | 6 +-- source/blender/nodes/shader/node_shader_tree.c | 44 ++++++++++++-------- .../nodes/shader/nodes/node_shader_common.c | 4 +- source/blender/nodes/texture/node_texture_tree.c | 40 +++++++++++------- .../nodes/texture/nodes/node_texture_common.c | 4 +- .../blender/render/intern/source/render_texture.c | 4 +- 13 files changed, 110 insertions(+), 71 deletions(-) diff --git a/source/blender/blenkernel/BKE_node.h b/source/blender/blenkernel/BKE_node.h index 7207fb7d0fb..1de3c295f4d 100644 --- a/source/blender/blenkernel/BKE_node.h +++ b/source/blender/blenkernel/BKE_node.h @@ -466,8 +466,8 @@ struct ShadeResult; /* API */ -struct bNodeTreeExec *ntreeShaderBeginExecTree(struct bNodeTree *ntree); -void ntreeShaderEndExecTree(struct bNodeTreeExec *exec); +struct bNodeTreeExec *ntreeShaderBeginExecTree(struct bNodeTree *ntree, int use_tree_data); +void ntreeShaderEndExecTree(struct bNodeTreeExec *exec, int use_tree_data); void ntreeShaderExecTree(struct bNodeTree *ntree, struct ShadeInput *shi, struct ShadeResult *shr); void ntreeShaderGetTexcoMode(struct bNodeTree *ntree, int osa, short *texco, int *mode); void nodeShaderSynchronizeID(struct bNode *node, int copyto); @@ -594,8 +594,8 @@ void ntreeGPUMaterialNodes(struct bNodeTree *ntree, struct GPUMaterial *mat); /* API */ struct CompBuf; -struct bNodeTreeExec *ntreeCompositBeginExecTree(struct bNodeTree *ntree); -void ntreeCompositEndExecTree(struct bNodeTreeExec *exec); +struct bNodeTreeExec *ntreeCompositBeginExecTree(struct bNodeTree *ntree, int use_tree_data); +void ntreeCompositEndExecTree(struct bNodeTreeExec *exec, int use_tree_data); void ntreeCompositExecTree(struct bNodeTree *ntree, struct RenderData *rd, int do_previews); void ntreeCompositTagRender(struct Scene *sce); int ntreeCompositTagAnimated(struct bNodeTree *ntree); @@ -642,8 +642,8 @@ void ntreeTexSetPreviewFlag(int); void ntreeTexCheckCyclics(struct bNodeTree *ntree); char* ntreeTexOutputMenu(struct bNodeTree *ntree); -struct bNodeTreeExec *ntreeTexBeginExecTree(struct bNodeTree *ntree); -void ntreeTexEndExecTree(struct bNodeTreeExec *exec); +struct bNodeTreeExec *ntreeTexBeginExecTree(struct bNodeTree *ntree, int use_tree_data); +void ntreeTexEndExecTree(struct bNodeTreeExec *exec, int use_tree_data); int ntreeTexExecTree(struct bNodeTree *ntree, struct TexResult *target, float *coord, float *dxt, float *dyt, int osatex, short thread, struct Tex *tex, short which_output, int cfra, int preview, struct ShadeInput *shi, struct MTex *mtex); diff --git a/source/blender/blenkernel/intern/material.c b/source/blender/blenkernel/intern/material.c index 36631d5af90..aab8e1abbea 100644 --- a/source/blender/blenkernel/intern/material.c +++ b/source/blender/blenkernel/intern/material.c @@ -926,7 +926,7 @@ void init_render_material(Material *mat, int r_mode, float *amb) init_render_nodetree(mat->nodetree, mat, r_mode, amb); if (!mat->nodetree->execdata) - mat->nodetree->execdata = ntreeShaderBeginExecTree(mat->nodetree); + mat->nodetree->execdata = ntreeShaderBeginExecTree(mat->nodetree, 1); } } @@ -960,7 +960,7 @@ void end_render_material(Material *mat) { if(mat && mat->nodetree && mat->use_nodes) { if (mat->nodetree->execdata) - ntreeShaderEndExecTree(mat->nodetree->execdata); + ntreeShaderEndExecTree(mat->nodetree->execdata, 1); } } diff --git a/source/blender/blenkernel/intern/node.c b/source/blender/blenkernel/intern/node.c index 481893b86a8..cd1a6e61151 100644 --- a/source/blender/blenkernel/intern/node.c +++ b/source/blender/blenkernel/intern/node.c @@ -897,13 +897,13 @@ void ntreeFreeTree(bNodeTree *ntree) if (ntree->execdata) { switch (ntree->type) { case NTREE_COMPOSIT: - ntreeCompositEndExecTree(ntree->execdata); + ntreeCompositEndExecTree(ntree->execdata, 1); break; case NTREE_SHADER: - ntreeShaderEndExecTree(ntree->execdata); + ntreeShaderEndExecTree(ntree->execdata, 1); break; case NTREE_TEXTURE: - ntreeTexEndExecTree(ntree->execdata); + ntreeTexEndExecTree(ntree->execdata, 1); break; } } diff --git a/source/blender/blenkernel/intern/texture.c b/source/blender/blenkernel/intern/texture.c index 6119a855366..38165182d83 100644 --- a/source/blender/blenkernel/intern/texture.c +++ b/source/blender/blenkernel/intern/texture.c @@ -767,7 +767,7 @@ Tex *copy_texture(Tex *tex) if(tex->nodetree) { if (tex->nodetree->execdata) { - ntreeTexEndExecTree(tex->nodetree->execdata); + ntreeTexEndExecTree(tex->nodetree->execdata, 1); } texn->nodetree= ntreeCopyTree(tex->nodetree); } diff --git a/source/blender/editors/sculpt_paint/paint_image.c b/source/blender/editors/sculpt_paint/paint_image.c index 9539706468f..79a3251cdf1 100644 --- a/source/blender/editors/sculpt_paint/paint_image.c +++ b/source/blender/editors/sculpt_paint/paint_image.c @@ -4664,7 +4664,7 @@ static void paint_brush_init_tex(Brush *brush) if(brush) { MTex *mtex= &brush->mtex; if(mtex->tex && mtex->tex->nodetree) - ntreeTexBeginExecTree(mtex->tex->nodetree); /* has internal flag to detect it only does it once */ + ntreeTexBeginExecTree(mtex->tex->nodetree, 1); /* has internal flag to detect it only does it once */ } } @@ -4806,7 +4806,7 @@ static void paint_brush_exit_tex(Brush *brush) if(brush) { MTex *mtex= &brush->mtex; if(mtex->tex && mtex->tex->nodetree) - ntreeTexEndExecTree(mtex->tex->nodetree->execdata); + ntreeTexEndExecTree(mtex->tex->nodetree->execdata, 1); } } diff --git a/source/blender/editors/sculpt_paint/sculpt.c b/source/blender/editors/sculpt_paint/sculpt.c index bf34a3b8c9f..ced3dd00a9c 100644 --- a/source/blender/editors/sculpt_paint/sculpt.c +++ b/source/blender/editors/sculpt_paint/sculpt.c @@ -3274,7 +3274,7 @@ static void sculpt_brush_init_tex(Sculpt *sd, SculptSession *ss) /* init mtex nodes */ if(mtex->tex && mtex->tex->nodetree) - ntreeTexBeginExecTree(mtex->tex->nodetree); /* has internal flag to detect it only does it once */ + ntreeTexBeginExecTree(mtex->tex->nodetree, 1); /* has internal flag to detect it only does it once */ /* TODO: Shouldn't really have to do this at the start of every stroke, but sculpt would need some sort of notification when @@ -3455,7 +3455,7 @@ static void sculpt_brush_exit_tex(Sculpt *sd) MTex *mtex= &brush->mtex; if(mtex->tex && mtex->tex->nodetree) - ntreeTexEndExecTree(mtex->tex->nodetree->execdata); + ntreeTexEndExecTree(mtex->tex->nodetree->execdata, 1); } static void sculpt_stroke_done(bContext *C, struct PaintStroke *UNUSED(stroke)) diff --git a/source/blender/nodes/composite/node_composite_tree.c b/source/blender/nodes/composite/node_composite_tree.c index 0ea62b0aa5f..4fc5e23e26a 100644 --- a/source/blender/nodes/composite/node_composite_tree.c +++ b/source/blender/nodes/composite/node_composite_tree.c @@ -200,17 +200,22 @@ bNodeTreeType ntreeType_Composite = { }; -struct bNodeTreeExec *ntreeCompositBeginExecTree(bNodeTree *ntree) +/* XXX Group nodes must set use_tree_data to false, since their trees can be shared by multiple nodes. + * If use_tree_data is true, the ntree->execdata pointer is checked to avoid multiple execution of top-level trees. + */ +struct bNodeTreeExec *ntreeCompositBeginExecTree(bNodeTree *ntree, int use_tree_data) { bNodeTreeExec *exec; bNode *node; bNodeSocket *sock; - /* XXX hack: prevent exec data from being generated twice. - * this should be handled by the renderer! - */ - if (ntree->execdata) - return ntree->execdata; + if (use_tree_data) { + /* XXX hack: prevent exec data from being generated twice. + * this should be handled by the renderer! + */ + if (ntree->execdata) + return ntree->execdata; + } /* ensures only a single output node is enabled */ ntreeSetOutput(ntree); @@ -236,15 +241,20 @@ struct bNodeTreeExec *ntreeCompositBeginExecTree(bNodeTree *ntree) } } - /* XXX this should not be necessary, but is still used for cmp/sha/tex nodes, + if (use_tree_data) { + /* XXX this should not be necessary, but is still used for cmp/sha/tex nodes, * which only store the ntree pointer. Should be fixed at some point! */ - ntree->execdata = exec; + ntree->execdata = exec; + } return exec; } -void ntreeCompositEndExecTree(bNodeTreeExec *exec) +/* XXX Group nodes must set use_tree_data to false, since their trees can be shared by multiple nodes. + * If use_tree_data is true, the ntree->execdata pointer is checked to avoid multiple execution of top-level trees. + */ +void ntreeCompositEndExecTree(bNodeTreeExec *exec, int use_tree_data) { if(exec) { bNodeTree *ntree= exec->nodetree; @@ -269,8 +279,10 @@ void ntreeCompositEndExecTree(bNodeTreeExec *exec) ntree_exec_end(exec); - /* XXX clear nodetree backpointer to exec data, same problem as noted in ntreeBeginExecTree */ - ntree->execdata = NULL; + if (use_tree_data) { + /* XXX clear nodetree backpointer to exec data, same problem as noted in ntreeBeginExecTree */ + ntree->execdata = NULL; + } } } @@ -495,10 +507,10 @@ static void ntree_composite_texnode(bNodeTree *ntree, int init) /* has internal flag to detect it only does it once */ if(init) { if (!tex->nodetree->execdata) - tex->nodetree->execdata = ntreeTexBeginExecTree(tex->nodetree); + tex->nodetree->execdata = ntreeTexBeginExecTree(tex->nodetree, 1); } else - ntreeTexEndExecTree(tex->nodetree->execdata); + ntreeTexEndExecTree(tex->nodetree->execdata, 1); tex->nodetree->execdata = NULL; } } @@ -521,8 +533,10 @@ void ntreeCompositExecTree(bNodeTree *ntree, RenderData *rd, int do_preview) if(do_preview) ntreeInitPreview(ntree, 0, 0); - if (!ntree->execdata) - exec = ntreeCompositBeginExecTree(ntree); + if (!ntree->execdata) { + /* XXX this is the top-level tree, so we use the ntree->execdata pointer. */ + exec = ntreeCompositBeginExecTree(ntree, 1); + } ntree_composite_texnode(ntree, 1); /* prevent unlucky accidents */ @@ -592,7 +606,8 @@ void ntreeCompositExecTree(bNodeTree *ntree, RenderData *rd, int do_preview) BLI_end_threads(&threads); - ntreeCompositEndExecTree(exec); + /* XXX top-level tree uses the ntree->execdata pointer */ + ntreeCompositEndExecTree(exec, 1); } /* *********************************************** */ diff --git a/source/blender/nodes/composite/nodes/node_composite_common.c b/source/blender/nodes/composite/nodes/node_composite_common.c index fbff8198dde..8067f7e92be 100644 --- a/source/blender/nodes/composite/nodes/node_composite_common.c +++ b/source/blender/nodes/composite/nodes/node_composite_common.c @@ -122,7 +122,7 @@ static void *group_initexec(bNode *node) bNodeStack *ns; /* initialize the internal node tree execution */ - exec = ntreeCompositBeginExecTree(ngroup); + exec = ntreeCompositBeginExecTree(ngroup, 0); /* tag group outputs as external to prevent freeing */ for (sock=ngroup->outputs.first; sock; sock=sock->next) { @@ -135,11 +135,11 @@ static void *group_initexec(bNode *node) return exec; } -static void group_freeexec(bNode *UNUSED(node), void *nodedata) +static void group_freeexec(bNode *node, void *nodedata) { bNodeTreeExec *gexec= (bNodeTreeExec*)nodedata; - ntreeCompositEndExecTree(gexec); + ntreeCompositEndExecTree(gexec, 0); } /* Copy inputs to the internal stack. diff --git a/source/blender/nodes/shader/node_shader_tree.c b/source/blender/nodes/shader/node_shader_tree.c index 8cb1ebeb15f..642e4be10d7 100644 --- a/source/blender/nodes/shader/node_shader_tree.c +++ b/source/blender/nodes/shader/node_shader_tree.c @@ -108,11 +108,11 @@ void ntreeGPUMaterialNodes(bNodeTree *ntree, GPUMaterial *mat) bNodeTreeExec *exec; if(!ntree->execdata) - exec = ntreeShaderBeginExecTree(ntree); + exec = ntreeShaderBeginExecTree(ntree, 1); ntreeExecGPUNodes(exec, mat, 1); - ntreeShaderEndExecTree(exec); + ntreeShaderEndExecTree(exec, 1); } /* **************** call to switch lamploop for material node ************ */ @@ -125,16 +125,21 @@ void set_node_shader_lamp_loop(void (*lamp_loop_func)(ShadeInput *, ShadeResult } -bNodeTreeExec *ntreeShaderBeginExecTree(bNodeTree *ntree) +/* XXX Group nodes must set use_tree_data to false, since their trees can be shared by multiple nodes. + * If use_tree_data is true, the ntree->execdata pointer is checked to avoid multiple execution of top-level trees. + */ +bNodeTreeExec *ntreeShaderBeginExecTree(bNodeTree *ntree, int use_tree_data) { bNodeTreeExec *exec; bNode *node; - /* XXX hack: prevent exec data from being generated twice. - * this should be handled by the renderer! - */ - if (ntree->execdata) - return ntree->execdata; + if (use_tree_data) { + /* XXX hack: prevent exec data from being generated twice. + * this should be handled by the renderer! + */ + if (ntree->execdata) + return ntree->execdata; + } /* ensures only a single output node is enabled */ ntreeSetOutput(ntree); @@ -148,15 +153,20 @@ bNodeTreeExec *ntreeShaderBeginExecTree(bNodeTree *ntree) for(node= exec->nodetree->nodes.first; node; node= node->next) node->need_exec= 1; - /* XXX this should not be necessary, but is still used for cmp/sha/tex nodes, - * which only store the ntree pointer. Should be fixed at some point! - */ - ntree->execdata = exec; + if (use_tree_data) { + /* XXX this should not be necessary, but is still used for cmp/sha/tex nodes, + * which only store the ntree pointer. Should be fixed at some point! + */ + ntree->execdata = exec; + } return exec; } -void ntreeShaderEndExecTree(bNodeTreeExec *exec) +/* XXX Group nodes must set use_tree_data to false, since their trees can be shared by multiple nodes. + * If use_tree_data is true, the ntree->execdata pointer is checked to avoid multiple execution of top-level trees. + */ +void ntreeShaderEndExecTree(bNodeTreeExec *exec, int use_tree_data) { if(exec) { bNodeTree *ntree= exec->nodetree; @@ -176,8 +186,10 @@ void ntreeShaderEndExecTree(bNodeTreeExec *exec) ntree_exec_end(exec); - /* XXX clear nodetree backpointer to exec data, same problem as noted in ntreeBeginExecTree */ - ntree->execdata = NULL; + if (use_tree_data) { + /* XXX clear nodetree backpointer to exec data, same problem as noted in ntreeBeginExecTree */ + ntree->execdata = NULL; + } } } @@ -199,7 +211,7 @@ void ntreeShaderExecTree(bNodeTree *ntree, ShadeInput *shi, ShadeResult *shr) memset(shr, 0, sizeof(ShadeResult)); if (!exec) - exec = ntree->execdata = ntreeShaderBeginExecTree(exec->nodetree); + exec = ntree->execdata = ntreeShaderBeginExecTree(exec->nodetree, 1); nts= ntreeGetThreadStack(exec, shi->thread); ntreeExecThreadNodes(exec, nts, &scd, shi->thread); diff --git a/source/blender/nodes/shader/nodes/node_shader_common.c b/source/blender/nodes/shader/nodes/node_shader_common.c index aa8e8241bf8..2dd15ab1e99 100644 --- a/source/blender/nodes/shader/nodes/node_shader_common.c +++ b/source/blender/nodes/shader/nodes/node_shader_common.c @@ -76,7 +76,7 @@ static void *group_initexec(bNode *node) bNodeTreeExec *exec; /* initialize the internal node tree execution */ - exec = ntreeShaderBeginExecTree(ngroup); + exec = ntreeShaderBeginExecTree(ngroup, 0); return exec; } @@ -85,7 +85,7 @@ static void group_freeexec(bNode *UNUSED(node), void *nodedata) { bNodeTreeExec*gexec= (bNodeTreeExec*)nodedata; - ntreeShaderEndExecTree(gexec); + ntreeShaderEndExecTree(gexec, 0); } /* Copy inputs to the internal stack. diff --git a/source/blender/nodes/texture/node_texture_tree.c b/source/blender/nodes/texture/node_texture_tree.c index 3ea15a316ab..603aa7ceb77 100644 --- a/source/blender/nodes/texture/node_texture_tree.c +++ b/source/blender/nodes/texture/node_texture_tree.c @@ -121,16 +121,21 @@ int ntreeTexTagAnimated(bNodeTree *ntree) return 0; } -bNodeTreeExec *ntreeTexBeginExecTree(bNodeTree *ntree) +/* XXX Group nodes must set use_tree_data to false, since their trees can be shared by multiple nodes. + * If use_tree_data is true, the ntree->execdata pointer is checked to avoid multiple execution of top-level trees. + */ +bNodeTreeExec *ntreeTexBeginExecTree(bNodeTree *ntree, int use_tree_data) { bNodeTreeExec *exec; bNode *node; - /* XXX hack: prevent exec data from being generated twice. - * this should be handled by the renderer! - */ - if (ntree->execdata) - return ntree->execdata; + if (use_tree_data) { + /* XXX hack: prevent exec data from being generated twice. + * this should be handled by the renderer! + */ + if (ntree->execdata) + return ntree->execdata; + } /* common base initialization */ exec = ntree_exec_begin(ntree); @@ -141,10 +146,12 @@ bNodeTreeExec *ntreeTexBeginExecTree(bNodeTree *ntree) for(node= exec->nodetree->nodes.first; node; node= node->next) node->need_exec= 1; - /* XXX this should not be necessary, but is still used for cmp/sha/tex nodes, - * which only store the ntree pointer. Should be fixed at some point! - */ - ntree->execdata = exec; + if (use_tree_data) { + /* XXX this should not be necessary, but is still used for cmp/sha/tex nodes, + * which only store the ntree pointer. Should be fixed at some point! + */ + ntree->execdata = exec; + } return exec; } @@ -163,7 +170,10 @@ static void tex_free_delegates(bNodeTreeExec *exec) MEM_freeN(ns->data); } -void ntreeTexEndExecTree(bNodeTreeExec *exec) +/* XXX Group nodes must set use_tree_data to false, since their trees can be shared by multiple nodes. + * If use_tree_data is true, the ntree->execdata pointer is checked to avoid multiple execution of top-level trees. + */ +void ntreeTexEndExecTree(bNodeTreeExec *exec, int use_tree_data) { if(exec) { bNodeTree *ntree= exec->nodetree; @@ -185,8 +195,10 @@ void ntreeTexEndExecTree(bNodeTreeExec *exec) ntree_exec_end(exec); - /* XXX clear nodetree backpointer to exec data, same problem as noted in ntreeBeginExecTree */ - ntree->execdata = NULL; + if (use_tree_data) { + /* XXX clear nodetree backpointer to exec data, same problem as noted in ntreeBeginExecTree */ + ntree->execdata = NULL; + } } } @@ -223,7 +235,7 @@ int ntreeTexExecTree( data.shi= shi; if (!exec) - exec = ntreeTexBeginExecTree(nodes); + exec = ntreeTexBeginExecTree(nodes, 1); nts= ntreeGetThreadStack(exec, thread); ntreeExecThreadNodes(exec, nts, &data, thread); diff --git a/source/blender/nodes/texture/nodes/node_texture_common.c b/source/blender/nodes/texture/nodes/node_texture_common.c index afb24226416..1b46b830909 100644 --- a/source/blender/nodes/texture/nodes/node_texture_common.c +++ b/source/blender/nodes/texture/nodes/node_texture_common.c @@ -61,7 +61,7 @@ static void *group_initexec(bNode *node) void *exec; /* initialize the internal node tree execution */ - exec = ntreeTexBeginExecTree(ngroup); + exec = ntreeTexBeginExecTree(ngroup, 0); return exec; } @@ -70,7 +70,7 @@ static void group_freeexec(bNode *UNUSED(node), void *nodedata) { bNodeTreeExec*gexec= (bNodeTreeExec*)nodedata; - ntreeTexEndExecTree(gexec); + ntreeTexEndExecTree(gexec, 0); } /* Copy inputs to the internal stack. diff --git a/source/blender/render/intern/source/render_texture.c b/source/blender/render/intern/source/render_texture.c index e35b3e53f5b..cf1fae81eb5 100644 --- a/source/blender/render/intern/source/render_texture.c +++ b/source/blender/render/intern/source/render_texture.c @@ -125,7 +125,7 @@ static void init_render_texture(Render *re, Tex *tex) } if(tex->nodetree && tex->use_nodes) { - ntreeTexBeginExecTree(tex->nodetree); /* has internal flag to detect it only does it once */ + ntreeTexBeginExecTree(tex->nodetree, 1); /* has internal flag to detect it only does it once */ } } @@ -145,7 +145,7 @@ void init_render_textures(Render *re) static void end_render_texture(Tex *tex) { if(tex && tex->use_nodes && tex->nodetree && tex->nodetree->execdata) - ntreeTexEndExecTree(tex->nodetree->execdata); + ntreeTexEndExecTree(tex->nodetree->execdata, 1); } void end_render_textures(Render *re) -- cgit v1.2.3 From 84b8ec2ec37e21f6672044c4bff1339365d76b55 Mon Sep 17 00:00:00 2001 From: Lukas Toenne Date: Tue, 6 Sep 2011 16:48:28 +0000 Subject: Fix for node group add menu, groups from old files wouldn't show up there. Reason was that node trees are now associated to specific node types (NODE_GROUP in particular) by the ntree->nodetype id. --- source/blender/blenloader/intern/readfile.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c index 66e38f1c5f8..d1a19f24b97 100644 --- a/source/blender/blenloader/intern/readfile.c +++ b/source/blender/blenloader/intern/readfile.c @@ -11991,6 +11991,17 @@ static void do_versions(FileData *fd, Library *lib, Main *main) ntree->update |= NTREE_UPDATE; } } + + { + /* Initialize group tree nodetypes. + * These are used to distinguish tree types and + * associate them with specific node types for polling. + */ + bNodeTree *ntree; + /* all node trees in main->nodetree are considered groups */ + for (ntree=main->nodetree.first; ntree; ntree=ntree->id.next) + ntree->nodetype = NODE_GROUP; + } } /* put compatibility code here until next subversion bump */ -- cgit v1.2.3 From c8a092789f5e53ebf418457bd2f7ea1a3818d0b7 Mon Sep 17 00:00:00 2001 From: Brecht Van Lommel Date: Tue, 6 Sep 2011 16:51:10 +0000 Subject: Node merge: some forward compatibility code to avoid crash loading files with node groups in older version, and to keep unconnected/default socket values. --- source/blender/blenloader/intern/writefile.c | 33 ++++++++++++++++++++++++++++ source/blender/makesdna/DNA_node_types.h | 6 ++--- 2 files changed, 36 insertions(+), 3 deletions(-) diff --git a/source/blender/blenloader/intern/writefile.c b/source/blender/blenloader/intern/writefile.c index b982630ec41..5c2d3e0c458 100644 --- a/source/blender/blenloader/intern/writefile.c +++ b/source/blender/blenloader/intern/writefile.c @@ -135,6 +135,7 @@ Any case: direct data is ALWAYS after the lib block #include "BLI_blenlib.h" #include "BLI_linklist.h" #include "BLI_bpath.h" +#include "BLI_math.h" #include "BLI_utildefines.h" #include "BKE_action.h" @@ -645,6 +646,38 @@ static void write_curvemapping(WriteData *wd, CurveMapping *cumap) static void write_node_socket(WriteData *wd, bNodeSocket *sock) { bNodeSocketType *stype= ntreeGetSocketType(sock->type); + + /* forward compatibility code, so older blenders still open */ + sock->stack_type = 1; + + if(sock->default_value) { + bNodeSocketValueFloat *valfloat; + bNodeSocketValueVector *valvector; + bNodeSocketValueRGBA *valrgba; + + switch (sock->type) { + case SOCK_FLOAT: + valfloat = sock->default_value; + sock->ns.vec[0] = valfloat->value; + sock->ns.min = valfloat->min; + sock->ns.max = valfloat->max; + break; + case SOCK_VECTOR: + valvector = sock->default_value; + copy_v3_v3(sock->ns.vec, valvector->value); + sock->ns.min = valvector->min; + sock->ns.max = valvector->max; + break; + case SOCK_RGBA: + valrgba = sock->default_value; + copy_v4_v4(sock->ns.vec, valrgba->value); + sock->ns.min = 0.0f; + sock->ns.max = 1.0f; + break; + } + } + + /* actual socket writing */ writestruct(wd, DATA, "bNodeSocket", 1, sock); if (sock->default_value) writestruct(wd, DATA, stype->value_structname, 1, sock->default_value); diff --git a/source/blender/makesdna/DNA_node_types.h b/source/blender/makesdna/DNA_node_types.h index 3a51a6a56a4..bac1e3cd8ca 100644 --- a/source/blender/makesdna/DNA_node_types.h +++ b/source/blender/makesdna/DNA_node_types.h @@ -84,7 +84,7 @@ typedef struct bNodeSocket { /* execution data */ short stack_index; /* local stack index */ - short pad2; + short stack_type; /* deprecated, kept for forward compatibility */ int pad3; void *cache; /* cached data from execution */ @@ -198,8 +198,8 @@ typedef struct bNodeLink { } bNodeLink; /* link->flag */ -#define NODE_LINK_VALID 1 /* link has been successfully validated */ -#define NODE_LINKFLAG_HILITE 2 +#define NODE_LINKFLAG_HILITE 1 /* link has been successfully validated */ +#define NODE_LINK_VALID 2 /* the basis for a Node tree, all links and nodes reside internal here */ /* only re-usable node trees are in the library though, materials and textures allocate own tree struct */ -- cgit v1.2.3 From 2ebc534900ab7ccaa37ec25dcc1aa24230fb1426 Mon Sep 17 00:00:00 2001 From: Brecht Van Lommel Date: Tue, 6 Sep 2011 17:18:50 +0000 Subject: Fix screen/scene browsing in info header not working right, mistake in code cleanup. --- source/blender/makesrna/intern/rna_screen.c | 8 +++++--- source/blender/makesrna/intern/rna_wm.c | 8 +++++--- 2 files changed, 10 insertions(+), 6 deletions(-) diff --git a/source/blender/makesrna/intern/rna_screen.c b/source/blender/makesrna/intern/rna_screen.c index 59707f05e6f..bd1021f038a 100644 --- a/source/blender/makesrna/intern/rna_screen.c +++ b/source/blender/makesrna/intern/rna_screen.c @@ -68,13 +68,14 @@ static void rna_Screen_scene_set(PointerRNA *ptr, PointerRNA value) sc->newscene= value.data; } -static void rna_Screen_scene_update(Main *UNUSED(bmain), Scene *UNUSED(scene), PointerRNA *ptr) +static void rna_Screen_scene_update(bContext *C, PointerRNA *ptr) { bScreen *sc= (bScreen*)ptr->data; - /* exception: can't set screens inside of area/region handers */ + /* exception: can't set screens inside of area/region handers, and must + use context so notifier gets to the right window */ if(sc->newscene) { - WM_main_add_notifier(NC_SCENE|ND_SCENEBROWSE, sc->newscene); + WM_event_add_notifier(C, NC_SCENE|ND_SCENEBROWSE, sc->newscene); sc->newscene= NULL; } } @@ -231,6 +232,7 @@ static void rna_def_screen(BlenderRNA *brna) RNA_def_property_flag(prop, PROP_EDITABLE|PROP_NEVER_NULL); RNA_def_property_pointer_funcs(prop, NULL, "rna_Screen_scene_set", NULL, NULL); RNA_def_property_ui_text(prop, "Scene", "Active scene to be edited in the screen"); + RNA_def_property_flag(prop, PROP_CONTEXT_UPDATE); RNA_def_property_update(prop, 0, "rna_Screen_scene_update"); /* collections */ diff --git a/source/blender/makesrna/intern/rna_wm.c b/source/blender/makesrna/intern/rna_wm.c index a595b121d1a..7ce1e1ab88f 100644 --- a/source/blender/makesrna/intern/rna_wm.c +++ b/source/blender/makesrna/intern/rna_wm.c @@ -482,13 +482,14 @@ static void rna_Window_screen_set(PointerRNA *ptr, PointerRNA value) win->newscreen= value.data; } -static void rna_Window_screen_update(Main *UNUSED(bmain), Scene *UNUSED(scene), PointerRNA *ptr) +static void rna_Window_screen_update(bContext *C, PointerRNA *ptr) { wmWindow *win= (wmWindow*)ptr->data; - /* exception: can't set screens inside of area/region handers */ + /* exception: can't set screens inside of area/region handers, and must + use context so notifier gets to the right window */ if(win->newscreen) { - WM_main_add_notifier(NC_SCREEN|ND_SCREENBROWSE, win->newscreen); + WM_event_add_notifier(C, NC_SCREEN|ND_SCREENBROWSE, win->newscreen); win->newscreen= NULL; } } @@ -1454,6 +1455,7 @@ static void rna_def_window(BlenderRNA *brna) RNA_def_property_ui_text(prop, "Screen", "Active screen showing in the window"); RNA_def_property_flag(prop, PROP_EDITABLE); RNA_def_property_pointer_funcs(prop, NULL, "rna_Window_screen_set", NULL, NULL); + RNA_def_property_flag(prop, PROP_CONTEXT_UPDATE); RNA_def_property_update(prop, 0, "rna_Window_screen_update"); } -- cgit v1.2.3 From 5700b1b1b24c42ac5c02b1da622d28bfefef6154 Mon Sep 17 00:00:00 2001 From: Brecht Van Lommel Date: Tue, 6 Sep 2011 17:27:18 +0000 Subject: Fix missing warning message when reading files that are not forward compatible, it seems this never worked in 2.5. --- source/blender/blenkernel/intern/blender.c | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/source/blender/blenkernel/intern/blender.c b/source/blender/blenkernel/intern/blender.c index 5f33059e117..2d4354bdd9f 100644 --- a/source/blender/blenkernel/intern/blender.c +++ b/source/blender/blenkernel/intern/blender.c @@ -324,17 +324,14 @@ static void setup_app_data(bContext *C, BlendFileData *bfd, const char *filepath MEM_freeN(bfd); } -static int handle_subversion_warning(Main *main) +static int handle_subversion_warning(Main *main, ReportList *reports) { if(main->minversionfile > BLENDER_VERSION || (main->minversionfile == BLENDER_VERSION && main->minsubversionfile > BLENDER_SUBVERSION)) { - - char str[128]; - - BLI_snprintf(str, sizeof(str), "File written by newer Blender binary: %d.%d , expect loss of data!", main->minversionfile, main->minsubversionfile); -// XXX error(str); + BKE_reportf(reports, RPT_ERROR, "File written by newer Blender binary: %d.%d , expect loss of data!", main->minversionfile, main->minsubversionfile); } + return 1; } @@ -392,7 +389,7 @@ int BKE_read_file(bContext *C, const char *filepath, ReportList *reports) if (bfd) { if(bfd->user) retval= BKE_READ_FILE_OK_USERPREFS; - if(0==handle_subversion_warning(bfd->main)) { + if(0==handle_subversion_warning(bfd->main, reports)) { free_main(bfd->main); MEM_freeN(bfd); bfd= NULL; -- cgit v1.2.3 From f2e236e312eb2e441e9869120165b316f0fddb44 Mon Sep 17 00:00:00 2001 From: Lukas Toenne Date: Tue, 6 Sep 2011 17:28:26 +0000 Subject: Enabled the 'Layout' node category, currently only containing the 'Frame' node. Both the category and the node could be renamed as needed. The frame node is largely experimental and not totally useful yet, but much asked for, so can't hurt to let people try it out. --- source/blender/editors/space_node/node_header.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/source/blender/editors/space_node/node_header.c b/source/blender/editors/space_node/node_header.c index 5c921d40344..7077f4a7497 100644 --- a/source/blender/editors/space_node/node_header.c +++ b/source/blender/editors/space_node/node_header.c @@ -232,6 +232,7 @@ static void node_menu_add(const bContext *C, Menu *menu) uiItemMenuF(layout, "Convertor", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_CONVERTOR)); uiItemMenuF(layout, "Group", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_GROUP)); uiItemMenuF(layout, "Dynamic", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_OP_DYNAMIC)); + uiItemMenuF(layout, "Layout", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_LAYOUT)); } else if(snode->treetype==NTREE_COMPOSIT) { uiItemMenuF(layout, "Input", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_INPUT)); @@ -243,6 +244,7 @@ static void node_menu_add(const bContext *C, Menu *menu) uiItemMenuF(layout, "Matte", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_MATTE)); uiItemMenuF(layout, "Distort", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_DISTORT)); uiItemMenuF(layout, "Group", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_GROUP)); + uiItemMenuF(layout, "Layout", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_LAYOUT)); } else if(snode->treetype==NTREE_TEXTURE) { uiItemMenuF(layout, "Input", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_INPUT)); @@ -253,6 +255,7 @@ static void node_menu_add(const bContext *C, Menu *menu) uiItemMenuF(layout, "Convertor", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_CONVERTOR)); uiItemMenuF(layout, "Distort", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_DISTORT)); uiItemMenuF(layout, "Group", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_GROUP)); + uiItemMenuF(layout, "Layout", 0, node_add_menu, SET_INT_IN_POINTER(NODE_CLASS_LAYOUT)); } } -- cgit v1.2.3 From decc2c2e774d11126d6006f9c4d4f37f2a09099d Mon Sep 17 00:00:00 2001 From: Brecht Van Lommel Date: Tue, 6 Sep 2011 17:34:56 +0000 Subject: Node merge: fix crash loading files with unknown nodes (e.g. cycles files). --- source/blender/blenkernel/intern/node.c | 6 ++++-- source/blender/blenloader/intern/readfile.c | 3 ++- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/source/blender/blenkernel/intern/node.c b/source/blender/blenkernel/intern/node.c index cd1a6e61151..47fc72f5e52 100644 --- a/source/blender/blenkernel/intern/node.c +++ b/source/blender/blenkernel/intern/node.c @@ -1524,9 +1524,11 @@ void NodeTagChanged(bNodeTree *ntree, bNode *node) { bNodeTreeType *ntreetype = ntreeGetType(ntree->type); - if (ntreetype->update_node) + /* extra null pointer checks here because this is called when unlinking + unknown nodes on file load, so typeinfo pointers may not be set */ + if (ntreetype && ntreetype->update_node) ntreetype->update_node(ntree, node); - else if (node->typeinfo->updatefunc) + else if (node->typeinfo && node->typeinfo->updatefunc) node->typeinfo->updatefunc(ntree, node); } diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c index d1a19f24b97..664148157cb 100644 --- a/source/blender/blenloader/intern/readfile.c +++ b/source/blender/blenloader/intern/readfile.c @@ -2217,8 +2217,9 @@ static void direct_link_nodetree(FileData *fd, bNodeTree *ntree) if(node->type == NODE_DYNAMIC) { node->custom1= 0; node->custom1= BSET(node->custom1, NODE_DYNAMIC_LOADED); - node->typeinfo= NULL; } + + node->typeinfo= NULL; link_list(fd, &node->inputs); link_list(fd, &node->outputs); -- cgit v1.2.3 From 53671577a4ead5e96889a5fcd5a04255f8c948de Mon Sep 17 00:00:00 2001 From: Sergey Sharybin Date: Tue, 6 Sep 2011 18:15:34 +0000 Subject: Fixed potential crash in NodeTagIDChanged. Discovered after merge trunk into tomato where there were no check for tree before calling this function. Old design worked fine with this. Mark some arguments as UNUSED. --- source/blender/blenkernel/intern/node.c | 4 +++- source/blender/nodes/composite/nodes/node_composite_common.c | 2 +- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/source/blender/blenkernel/intern/node.c b/source/blender/blenkernel/intern/node.c index 47fc72f5e52..292f38b9472 100644 --- a/source/blender/blenkernel/intern/node.c +++ b/source/blender/blenkernel/intern/node.c @@ -1534,13 +1534,15 @@ void NodeTagChanged(bNodeTree *ntree, bNode *node) int NodeTagIDChanged(bNodeTree *ntree, ID *id) { - bNodeTreeType *ntreetype = ntreeGetType(ntree->type); + bNodeTreeType *ntreetype; bNode *node; int change = FALSE; if(ELEM(NULL, id, ntree)) return change; + ntreetype = ntreeGetType(ntree->type); + if (ntreetype->update_node) { for(node= ntree->nodes.first; node; node= node->next) { if(node->id==id) { diff --git a/source/blender/nodes/composite/nodes/node_composite_common.c b/source/blender/nodes/composite/nodes/node_composite_common.c index 8067f7e92be..d5ae442c25f 100644 --- a/source/blender/nodes/composite/nodes/node_composite_common.c +++ b/source/blender/nodes/composite/nodes/node_composite_common.c @@ -135,7 +135,7 @@ static void *group_initexec(bNode *node) return exec; } -static void group_freeexec(bNode *node, void *nodedata) +static void group_freeexec(bNode *UNUSED(node), void *nodedata) { bNodeTreeExec *gexec= (bNodeTreeExec*)nodedata; -- cgit v1.2.3 From 813d09cb5904bd435a6eefa328314d3cb9076be8 Mon Sep 17 00:00:00 2001 From: Joerg Mueller Date: Tue, 6 Sep 2011 21:02:26 +0000 Subject: BGE fix: ignore sounds that cannot be opened instead of crashing. ;-) --- source/gameengine/Converter/KX_ConvertActuators.cpp | 21 ++++++++++++++------- source/gameengine/Ketsji/KX_SoundActuator.cpp | 10 +++++++++- 2 files changed, 23 insertions(+), 8 deletions(-) diff --git a/source/gameengine/Converter/KX_ConvertActuators.cpp b/source/gameengine/Converter/KX_ConvertActuators.cpp index 8fc224fba6f..6ba178cbb2f 100644 --- a/source/gameengine/Converter/KX_ConvertActuators.cpp +++ b/source/gameengine/Converter/KX_ConvertActuators.cpp @@ -413,14 +413,21 @@ void BL_ConvertActuators(char* maggiename, // if sound shall be 3D but isn't mono, we have to make it mono! if(is3d) { - AUD_Reference reader = snd_sound->createReader(); - if(reader->getSpecs().channels != AUD_CHANNELS_MONO) + try { - AUD_DeviceSpecs specs; - specs.channels = AUD_CHANNELS_MONO; - specs.rate = AUD_RATE_INVALID; - specs.format = AUD_FORMAT_INVALID; - snd_sound = new AUD_ChannelMapperFactory(snd_sound, specs); + AUD_Reference reader = snd_sound->createReader(); + if(reader->getSpecs().channels != AUD_CHANNELS_MONO) + { + AUD_DeviceSpecs specs; + specs.channels = AUD_CHANNELS_MONO; + specs.rate = AUD_RATE_INVALID; + specs.format = AUD_FORMAT_INVALID; + snd_sound = new AUD_ChannelMapperFactory(snd_sound, specs); + } + } + catch(AUD_Exception&) + { + // sound cannot be played... ignore } } } diff --git a/source/gameengine/Ketsji/KX_SoundActuator.cpp b/source/gameengine/Ketsji/KX_SoundActuator.cpp index 6c7b515c095..f24243fcdfc 100644 --- a/source/gameengine/Ketsji/KX_SoundActuator.cpp +++ b/source/gameengine/Ketsji/KX_SoundActuator.cpp @@ -108,7 +108,15 @@ void KX_SoundActuator::play() break; } - m_handle = AUD_getDevice()->play(sound, 0); + try + { + m_handle = AUD_getDevice()->play(sound, 0); + } + catch(AUD_Exception&) + { + // cannot play back, ignore + return; + } AUD_Reference handle3d = AUD_Reference(m_handle); -- cgit v1.2.3 From 9baff83d72ccb287e2e6011c648877b96790e9a9 Mon Sep 17 00:00:00 2001 From: Nathan Letwory Date: Tue, 6 Sep 2011 22:18:12 +0000 Subject: Split off scene export code. --- source/blender/collada/CMakeLists.txt | 2 + source/blender/collada/DocumentExporter.cpp | 162 +--------------------------- source/blender/collada/SceneExporter.cpp | 161 +++++++++++++++++++++++++++ source/blender/collada/SceneExporter.h | 101 +++++++++++++++++ 4 files changed, 267 insertions(+), 159 deletions(-) create mode 100644 source/blender/collada/SceneExporter.cpp create mode 100644 source/blender/collada/SceneExporter.h diff --git a/source/blender/collada/CMakeLists.txt b/source/blender/collada/CMakeLists.txt index d73373aa901..cc7229383e3 100644 --- a/source/blender/collada/CMakeLists.txt +++ b/source/blender/collada/CMakeLists.txt @@ -61,6 +61,7 @@ set(SRC MaterialExporter.cpp MeshImporter.cpp SkinInfo.cpp + SceneExporter.cpp TransformReader.cpp TransformWriter.cpp collada.cpp @@ -85,6 +86,7 @@ set(SRC MaterialExporter.h MeshImporter.h SkinInfo.h + SceneExporter.h TransformReader.h TransformWriter.h collada.h diff --git a/source/blender/collada/DocumentExporter.cpp b/source/blender/collada/DocumentExporter.cpp index 6e780889d16..85f37d29f22 100644 --- a/source/blender/collada/DocumentExporter.cpp +++ b/source/blender/collada/DocumentExporter.cpp @@ -34,6 +34,7 @@ extern "C" { #include "DNA_scene_types.h" #include "DNA_object_types.h" +#include "DNA_group_types.h" #include "DNA_meshdata_types.h" #include "DNA_mesh_types.h" #include "DNA_image_types.h" @@ -104,6 +105,7 @@ extern char build_rev[]; #include "COLLADASWConstants.h" #include "COLLADASWLibraryControllers.h" #include "COLLADASWInstanceController.h" +#include "COLLADASWInstanceNode.h" #include "COLLADASWBaseInputElement.h" #include "collada_internal.h" @@ -113,6 +115,7 @@ extern char build_rev[]; #include "InstanceWriter.h" #include "TransformWriter.h" +#include "SceneExporter.h" #include "ArmatureExporter.h" #include "AnimationExporter.h" #include "CameraExporter.h" @@ -142,165 +145,6 @@ char *bc_CustomData_get_active_layer_name(const CustomData *data, int type) return data->layers[layer_index].name; } - -/* - Utilities to avoid code duplication. - Definition can take some time to understand, but they should be useful. -*/ - - -template -void forEachObjectInScene(Scene *sce, Functor &f) -{ - Base *base= (Base*) sce->base.first; - while(base) { - Object *ob = base->object; - - f(ob); - - base= base->next; - } -} - - - -class SceneExporter: COLLADASW::LibraryVisualScenes, protected TransformWriter, protected InstanceWriter -{ - ArmatureExporter *arm_exporter; -public: - SceneExporter(COLLADASW::StreamWriter *sw, ArmatureExporter *arm) : COLLADASW::LibraryVisualScenes(sw), - arm_exporter(arm) {} - - void exportScene(Scene *sce, bool export_selected) { - // - std::string id_naming = id_name(sce); - openVisualScene(translate_id(id_naming), id_naming); - - // write s - //forEachMeshObjectInScene(sce, *this); - //forEachCameraObjectInScene(sce, *this); - //forEachLampObjectInScene(sce, *this); - exportHierarchy(sce, export_selected); - - // - closeVisualScene(); - - closeLibrary(); - } - - void exportHierarchy(Scene *sce, bool export_selected) - { - Base *base= (Base*) sce->base.first; - while(base) { - Object *ob = base->object; - - if (!ob->parent) { - if(sce->lay & ob->lay) { - switch(ob->type) { - case OB_MESH: - case OB_CAMERA: - case OB_LAMP: - case OB_ARMATURE: - case OB_EMPTY: - if (export_selected && !(ob->flag & SELECT)) { - break; - } - // write nodes.... - writeNodes(ob, sce); - break; - } - } - } - - base= base->next; - } - } - - - // called for each object - //void operator()(Object *ob) { - void writeNodes(Object *ob, Scene *sce) - { - COLLADASW::Node node(mSW); - node.setNodeId(translate_id(id_name(ob))); - node.setType(COLLADASW::Node::NODE); - - node.start(); - - bool is_skinned_mesh = arm_exporter->is_skinned_mesh(ob); - - if (ob->type == OB_MESH && is_skinned_mesh) - // for skinned mesh we write obmat in - TransformWriter::add_node_transform_identity(node); - else - TransformWriter::add_node_transform_ob(node, ob); - - // - if (ob->type == OB_MESH) { - if (is_skinned_mesh) { - arm_exporter->add_instance_controller(ob); - } - else { - COLLADASW::InstanceGeometry instGeom(mSW); - instGeom.setUrl(COLLADASW::URI(COLLADABU::Utils::EMPTY_STRING, get_geometry_id(ob))); - - InstanceWriter::add_material_bindings(instGeom.getBindMaterial(), ob); - - instGeom.add(); - } - } - - // - else if (ob->type == OB_ARMATURE) { - arm_exporter->add_armature_bones(ob, sce); - - // XXX this looks unstable... - node.end(); - } - - // - else if (ob->type == OB_CAMERA) { - COLLADASW::InstanceCamera instCam(mSW, COLLADASW::URI(COLLADABU::Utils::EMPTY_STRING, get_camera_id(ob))); - instCam.add(); - } - - // - else if (ob->type == OB_LAMP) { - COLLADASW::InstanceLight instLa(mSW, COLLADASW::URI(COLLADABU::Utils::EMPTY_STRING, get_light_id(ob))); - instLa.add(); - } - - // empty object - else if (ob->type == OB_EMPTY) { - } - - // write nodes for child objects - Base *b = (Base*) sce->base.first; - while(b) { - // cob - child object - Object *cob = b->object; - - if (cob->parent == ob) { - switch(cob->type) { - case OB_MESH: - case OB_CAMERA: - case OB_LAMP: - case OB_EMPTY: - case OB_ARMATURE: - // write node... - writeNodes(cob, sce); - break; - } - } - - b = b->next; - } - - if (ob->type != OB_ARMATURE) - node.end(); - } -}; - // TODO: it would be better to instantiate animations rather than create a new one per object // COLLADA allows this through multiple s in . // For this to work, we need to know objects that use a certain action. diff --git a/source/blender/collada/SceneExporter.cpp b/source/blender/collada/SceneExporter.cpp new file mode 100644 index 00000000000..96f20ac21c3 --- /dev/null +++ b/source/blender/collada/SceneExporter.cpp @@ -0,0 +1,161 @@ +/* + * $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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + * Contributor(s): Chingiz Dyussenov, Arystanbek Dyussenov, Jan Diederich, Tod Liverseed. + * + * ***** END GPL LICENSE BLOCK ***** + */ + +/** \file blender/collada/SceneExporter.cpp + * \ingroup collada + */ + +#include "SceneExporter.h" + +SceneExporter::SceneExporter(COLLADASW::StreamWriter *sw, ArmatureExporter *arm) + : COLLADASW::LibraryVisualScenes(sw), arm_exporter(arm) +{} + +void SceneExporter::exportScene(Scene *sce, bool export_selected) +{ + // + std::string id_naming = id_name(sce); + openVisualScene(translate_id(id_naming), id_naming); + exportHierarchy(sce, export_selected); + closeVisualScene(); + closeLibrary(); +} + +void SceneExporter::exportHierarchy(Scene *sce, bool export_selected) +{ + Base *base= (Base*) sce->base.first; + while(base) { + Object *ob = base->object; + + if (!ob->parent) { + if(sce->lay & ob->lay) { + switch(ob->type) { + case OB_MESH: + case OB_CAMERA: + case OB_LAMP: + case OB_ARMATURE: + case OB_EMPTY: + if (export_selected && !(ob->flag & SELECT)) { + break; + } + // write nodes.... + writeNodes(ob, sce); + break; + } + } + } + + base= base->next; + } +} + +void SceneExporter::writeNodes(Object *ob, Scene *sce) +{ + COLLADASW::Node node(mSW); + node.setNodeId(translate_id(id_name(ob))); + node.setType(COLLADASW::Node::NODE); + + node.start(); + + bool is_skinned_mesh = arm_exporter->is_skinned_mesh(ob); + + if (ob->type == OB_MESH && is_skinned_mesh) + // for skinned mesh we write obmat in + TransformWriter::add_node_transform_identity(node); + else + TransformWriter::add_node_transform_ob(node, ob); + + // + if (ob->type == OB_MESH) { + if (is_skinned_mesh) { + arm_exporter->add_instance_controller(ob); + } + else { + COLLADASW::InstanceGeometry instGeom(mSW); + instGeom.setUrl(COLLADASW::URI(COLLADABU::Utils::EMPTY_STRING, get_geometry_id(ob))); + + InstanceWriter::add_material_bindings(instGeom.getBindMaterial(), ob); + + instGeom.add(); + } + } + + // + else if (ob->type == OB_ARMATURE) { + arm_exporter->add_armature_bones(ob, sce); + + // XXX this looks unstable... + node.end(); + } + + // + else if (ob->type == OB_CAMERA) { + COLLADASW::InstanceCamera instCam(mSW, COLLADASW::URI(COLLADABU::Utils::EMPTY_STRING, get_camera_id(ob))); + instCam.add(); + } + + // + else if (ob->type == OB_LAMP) { + COLLADASW::InstanceLight instLa(mSW, COLLADASW::URI(COLLADABU::Utils::EMPTY_STRING, get_light_id(ob))); + instLa.add(); + } + + // empty object + else if (ob->type == OB_EMPTY) { // TODO: handle groups (OB_DUPLIGROUP + if((ob->transflag & OB_DUPLIGROUP) == OB_DUPLIGROUP && ob->dup_group) { + GroupObject *go = NULL; + Group *gr = ob->dup_group; + printf("group detected %u\n", gr); + for(go = (GroupObject*)(gr->gobject.first); go; go=go->next) { + printf("\t%s\n", go->ob->id.name); + } + } + } + + // write nodes for child objects + Base *b = (Base*) sce->base.first; + while(b) { + // cob - child object + Object *cob = b->object; + + if (cob->parent == ob) { + switch(cob->type) { + case OB_MESH: + case OB_CAMERA: + case OB_LAMP: + case OB_EMPTY: + case OB_ARMATURE: + // write node... + writeNodes(cob, sce); + break; + } + } + + b = b->next; + } + + if (ob->type != OB_ARMATURE) + node.end(); +} + diff --git a/source/blender/collada/SceneExporter.h b/source/blender/collada/SceneExporter.h new file mode 100644 index 00000000000..30fef924ffd --- /dev/null +++ b/source/blender/collada/SceneExporter.h @@ -0,0 +1,101 @@ +/* + * $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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + * Contributor(s): Chingiz Dyussenov, Arystanbek Dyussenov. + * + * ***** END GPL LICENSE BLOCK ***** + */ + +/** \file SceneExporter.h + * \ingroup collada + */ + +#ifndef __SCENEEXPORTER_H__ +#define __SCENEEXPORTER_H__ + +extern "C" { +#include "DNA_scene_types.h" +#include "DNA_object_types.h" +#include "DNA_group_types.h" +#include "DNA_meshdata_types.h" +#include "DNA_mesh_types.h" +#include "DNA_image_types.h" +#include "DNA_material_types.h" +#include "DNA_texture_types.h" +#include "DNA_anim_types.h" +#include "DNA_action_types.h" +#include "DNA_curve_types.h" +#include "DNA_armature_types.h" +#include "DNA_modifier_types.h" +#include "DNA_userdef_types.h" + +#include "BKE_DerivedMesh.h" +#include "BKE_fcurve.h" +#include "BKE_animsys.h" +#include "BLI_path_util.h" +#include "BLI_fileops.h" +#include "ED_keyframing.h" +} + +#include "COLLADASWAsset.h" +#include "COLLADASWLibraryVisualScenes.h" +#include "COLLADASWNode.h" +#include "COLLADASWSource.h" +#include "COLLADASWInstanceGeometry.h" +#include "COLLADASWInputList.h" +#include "COLLADASWPrimitves.h" +#include "COLLADASWVertices.h" +#include "COLLADASWLibraryAnimations.h" +#include "COLLADASWLibraryImages.h" +#include "COLLADASWLibraryEffects.h" +#include "COLLADASWImage.h" +#include "COLLADASWEffectProfile.h" +#include "COLLADASWColorOrTexture.h" +#include "COLLADASWParamTemplate.h" +#include "COLLADASWParamBase.h" +#include "COLLADASWSurfaceInitOption.h" +#include "COLLADASWSampler.h" +#include "COLLADASWScene.h" +#include "COLLADASWTechnique.h" +#include "COLLADASWTexture.h" +#include "COLLADASWLibraryMaterials.h" +#include "COLLADASWBindMaterial.h" +#include "COLLADASWInstanceCamera.h" +#include "COLLADASWInstanceLight.h" +#include "COLLADASWConstants.h" +#include "COLLADASWLibraryControllers.h" +#include "COLLADASWInstanceController.h" +#include "COLLADASWInstanceNode.h" +#include "COLLADASWBaseInputElement.h" + +#include "ArmatureExporter.h" + +class SceneExporter: COLLADASW::LibraryVisualScenes, protected TransformWriter, protected InstanceWriter +{ + ArmatureExporter *arm_exporter; +public: + SceneExporter(COLLADASW::StreamWriter *sw, ArmatureExporter *arm); + void exportScene(Scene *sce, bool export_selected); + +private: + void exportHierarchy(Scene *sce, bool export_selected); + void writeNodes(Object *ob, Scene *sce); +}; + +#endif -- cgit v1.2.3 From 9161d3ce4bdd7c838751462b47eb045ea33a686e Mon Sep 17 00:00:00 2001 From: Campbell Barton Date: Tue, 6 Sep 2011 23:46:20 +0000 Subject: use Py_ssize_t rather than int when dealing with list sizes (original patch from Fedora but applied changes elsewhere too), also replace PyList_Size with PyList_GET_SIZE where typechecking is already done. --- source/blender/python/generic/bpy_internal_import.c | 4 ++-- source/blender/python/intern/bpy_rna.c | 2 +- source/blender/python/mathutils/mathutils_geometry.c | 12 ++++++------ source/gameengine/BlenderRoutines/BL_KetsjiEmbedStart.cpp | 5 +++-- source/gameengine/Expressions/ListValue.cpp | 4 ++-- source/gameengine/Expressions/Value.cpp | 4 ++-- source/gameengine/Ketsji/KX_PythonInit.cpp | 6 +++--- source/gameengine/Ketsji/KX_Scene.cpp | 4 ++-- 8 files changed, 21 insertions(+), 20 deletions(-) diff --git a/source/blender/python/generic/bpy_internal_import.c b/source/blender/python/generic/bpy_internal_import.c index f0158fe72c3..67ed90c79eb 100644 --- a/source/blender/python/generic/bpy_internal_import.c +++ b/source/blender/python/generic/bpy_internal_import.c @@ -344,7 +344,7 @@ void bpy_text_clear_modules(int clear_all) /* looping over the dict */ PyObject *key, *value; - int pos= 0; + Py_ssize_t pos= 0; /* new list */ PyObject *list; @@ -374,7 +374,7 @@ void bpy_text_clear_modules(int clear_all) } /* remove all our modules */ - for(pos=0; pos < PyList_Size(list); pos++) { + for(pos=0; pos < PyList_GET_SIZE(list); pos++) { /* PyObject_Print(key, stderr, 0); */ key= PyList_GET_ITEM(list, pos); PyDict_DelItem(modules, key); diff --git a/source/blender/python/intern/bpy_rna.c b/source/blender/python/intern/bpy_rna.c index d10c8c843e8..2212499d842 100644 --- a/source/blender/python/intern/bpy_rna.c +++ b/source/blender/python/intern/bpy_rna.c @@ -4608,7 +4608,7 @@ static PyObject *pyrna_func_call(BPy_FunctionRNA *self, PyObject *args, PyObject #ifdef DEBUG_STRING_FREE - // if(PyList_Size(string_free_ls)) printf("%.200s.%.200s(): has %d strings\n", RNA_struct_identifier(self_ptr->type), RNA_function_identifier(self_func), (int)PyList_Size(string_free_ls)); + // if(PyList_GET_SIZE(string_free_ls)) printf("%.200s.%.200s(): has %d strings\n", RNA_struct_identifier(self_ptr->type), RNA_function_identifier(self_func), (int)PyList_GET_SIZE(string_free_ls)); Py_DECREF(string_free_ls); #undef DEBUG_STRING_FREE #endif diff --git a/source/blender/python/mathutils/mathutils_geometry.c b/source/blender/python/mathutils/mathutils_geometry.c index bcdfe020e1a..0394d732ae3 100644 --- a/source/blender/python/mathutils/mathutils_geometry.c +++ b/source/blender/python/mathutils/mathutils_geometry.c @@ -983,7 +983,7 @@ static PyObject *M_Geometry_tesselate_polygon(PyObject *UNUSED(self), PyObject * static int boxPack_FromPyObject(PyObject *value, boxPack **boxarray) { - int len, i; + Py_ssize_t len, i; PyObject *list_item, *item_1, *item_2; boxPack *box; @@ -995,14 +995,14 @@ static int boxPack_FromPyObject(PyObject *value, boxPack **boxarray) return -1; } - len= PyList_Size(value); + len= PyList_GET_SIZE(value); (*boxarray)= MEM_mallocN(len*sizeof(boxPack), "boxPack box"); for(i= 0; i < len; i++) { list_item= PyList_GET_ITEM(value, i); - if(!PyList_Check(list_item) || PyList_Size(list_item) < 4) { + if(!PyList_Check(list_item) || PyList_GET_SIZE(list_item) < 4) { MEM_freeN(*boxarray); PyErr_SetString(PyExc_TypeError, "can only pack a list of [x, y, w, h]"); @@ -1034,11 +1034,11 @@ static int boxPack_FromPyObject(PyObject *value, boxPack **boxarray) static void boxPack_ToPyObject(PyObject *value, boxPack **boxarray) { - int len, i; + Py_ssize_t len, i; PyObject *list_item; boxPack *box; - len= PyList_Size(value); + len= PyList_GET_SIZE(value); for(i= 0; i < len; i++) { box= (*boxarray)+i; @@ -1062,7 +1062,7 @@ PyDoc_STRVAR(M_Geometry_box_pack_2d_doc, static PyObject *M_Geometry_box_pack_2d(PyObject *UNUSED(self), PyObject *boxlist) { float tot_width= 0.0f, tot_height= 0.0f; - int len; + Py_ssize_t len; PyObject *ret; diff --git a/source/gameengine/BlenderRoutines/BL_KetsjiEmbedStart.cpp b/source/gameengine/BlenderRoutines/BL_KetsjiEmbedStart.cpp index 40f1701e44a..810e9b6ddfb 100644 --- a/source/gameengine/BlenderRoutines/BL_KetsjiEmbedStart.cpp +++ b/source/gameengine/BlenderRoutines/BL_KetsjiEmbedStart.cpp @@ -507,9 +507,10 @@ extern "C" void StartKetsjiShell(struct bContext *C, struct ARegion *ar, rcti *c //PyDict_Clear(PyModule_GetDict(gameLogic)); // Keep original items, means python plugins will autocomplete members - int listIndex; PyObject *gameLogic_keys_new = PyDict_Keys(PyModule_GetDict(gameLogic)); - for (listIndex=0; listIndex < PyList_Size(gameLogic_keys_new); listIndex++) { + const Py_ssize_t numitems= PyList_GET_SIZE(gameLogic_keys_new); + Py_ssize_t listIndex; + for (listIndex=0; listIndex < numitems; listIndex++) { PyObject* item = PyList_GET_ITEM(gameLogic_keys_new, listIndex); if (!PySequence_Contains(gameLogic_keys, item)) { PyDict_DelItem( PyModule_GetDict(gameLogic), item); diff --git a/source/gameengine/Expressions/ListValue.cpp b/source/gameengine/Expressions/ListValue.cpp index 271d5067dd9..934f2a8dd87 100644 --- a/source/gameengine/Expressions/ListValue.cpp +++ b/source/gameengine/Expressions/ListValue.cpp @@ -387,7 +387,7 @@ PyObject* listvalue_buffer_slice(PyObject* self,Py_ssize_t ilow, Py_ssize_t ihig static PyObject *listvalue_buffer_concat(PyObject * self, PyObject * other) { CListValue *listval= static_cast(BGE_PROXY_REF(self)); - int i, numitems, numitems_orig; + Py_ssize_t i, numitems, numitems_orig; if (listval==NULL) { PyErr_SetString(PyExc_SystemError, "CList+other, "BGE_PROXY_ERROR_MSG); @@ -408,7 +408,7 @@ static PyObject *listvalue_buffer_concat(PyObject * self, PyObject * other) CValue* listitemval; bool error = false; - numitems = PyList_Size(other); + numitems = PyList_GET_SIZE(other); /* copy the first part of the list */ listval_new->Resize(numitems_orig + numitems); diff --git a/source/gameengine/Expressions/Value.cpp b/source/gameengine/Expressions/Value.cpp index e60b380e95c..41c0850a779 100644 --- a/source/gameengine/Expressions/Value.cpp +++ b/source/gameengine/Expressions/Value.cpp @@ -546,8 +546,8 @@ CValue* CValue::ConvertPythonToValue(PyObject* pyobj, const char *error_prefix) CListValue* listval = new CListValue(); bool error = false; - int i; - int numitems = PyList_Size(pyobj); + Py_ssize_t i; + Py_ssize_t numitems = PyList_GET_SIZE(pyobj); for (i=0;iGetSceneConverter()->ConvertMeshSpecial(kx_scene, maggie, name); @@ -1751,7 +1751,7 @@ static void initPySysObjects(Main *maggie) initPySysObjects__append(sys_path, gp_GamePythonPath); -// fprintf(stderr, "\nNew Path: %d ", PyList_Size(sys_path)); +// fprintf(stderr, "\nNew Path: %d ", PyList_GET_SIZE(sys_path)); // PyObject_Print(sys_path, stderr, 0); } @@ -1775,7 +1775,7 @@ static void restorePySysObjects(void) gp_OrigPythonSysModules= NULL; -// fprintf(stderr, "\nRestore Path: %d ", PyList_Size(sys_path)); +// fprintf(stderr, "\nRestore Path: %d ", PyList_GET_SIZE(sys_path)); // PyObject_Print(sys_path, stderr, 0); } diff --git a/source/gameengine/Ketsji/KX_Scene.cpp b/source/gameengine/Ketsji/KX_Scene.cpp index 06e343cedb2..7c76ab01e93 100644 --- a/source/gameengine/Ketsji/KX_Scene.cpp +++ b/source/gameengine/Ketsji/KX_Scene.cpp @@ -1916,7 +1916,7 @@ void KX_Scene::Render2DFilters(RAS_ICanvas* canvas) void KX_Scene::RunDrawingCallbacks(PyObject* cb_list) { - int len; + Py_ssize_t len; if (cb_list && (len=PyList_GET_SIZE(cb_list))) { @@ -1925,7 +1925,7 @@ void KX_Scene::RunDrawingCallbacks(PyObject* cb_list) PyObject* ret; // Iterate the list and run the callbacks - for (int pos=0; pos < len; pos++) + for (Py_ssize_t pos=0; pos < len; pos++) { func= PyList_GET_ITEM(cb_list, pos); ret= PyObject_Call(func, args, NULL); -- cgit v1.2.3