Freestyle integration into Blender

December 1, 2008

Support for Python's native iterator protocol

Filed under: Update — The dev team @ 12:20 PM

As a preliminary first step towards full support for Python’s native iterator protocol in Freestyle, Stroke and StrokeVertexIterator (used in the shade() method of a StrokeShader implementation) have been improved to adhere to the iterator protocol as follows:

  • Stroke object has __len__() and __getitem__() methods so that subscript can be used, like stroke[0] and stroke[-1].
  • stroke.StrokeVerticesBegin() and stroke.StrokeVerticesEnd() return iterable objects (having next() method).
  • “for v in stroke.StrokeVerticesBegin()” is equivalent to “for v in stroke”.

The conventional C++/SWIG-based syntax is still usable, so programmers can choose a preferable syntax.

Simple iteration

C++/SWIG-based syntax:

    it = stroke.StrokeVerticesBegin()
    while it.isEnd() == 0:
        v = it.getObject()
        v.attribute().setThickness(...)
        it.increment()

New syntax #1:

    for v in stroke:
        v.attribute().setThickness(...)

New syntax #2:

    for v in stroke.strokeVerticesBegin():
        v.attribute().setThickness(...)

The strokeVerticesBegin() method takes an optional argument for resampling (the default value is 0, which means no resampling).  The second syntax is useful when the optional argument is specified.

Reverse iteration

C++/SWIG-based syntax:

    it = stroke.StrokeVerticesEnd()
    while it.isBegin() == 0:
        it.decrement()
        v = it.getObject()
        v.attribute().setThickness(...)

New syntax:

    for v in stroke.StrokeVerticesEnd():
        v.attribute().setThickness(...)

Getting the first StrokeVertex

C++/SWIG-based syntax:

    it = stroke.StrokeVerticesBegin()
        v = it.getObject()

New syntax:

    v = stroke[0]

Getting the last StrokeVertex

C++/SWIG-based syntax:

    it = stroke.StrokeVerticesEnd()
        it.decrement()
        v = it.getObject()

New syntax:

    v = stroke[-1]

Getting the number of vertices

C++/SWIG-based syntax:

    n = stroke.StrokeVerticeSize()

New syntax:

    n = len(stroke)

Removing vertices during iteration

There are needs to remove some vertices during iteration.  However, the following code will not work, since the removal of vertices may confuse the iteration.

Incorrect code:

    for vertex in stroke:
        if some condition holds:
            stroke.RemoveVertex(vertex)

If an API were designed so as to make this work, stroke.__iter__() would always have to return a copy of the sequence of vertices, which would be expensive in many cases where the removal of vertices is not necessary.

So, a compromised API design has been taken as follows:

  • stroke.__iter__() returns a reference to the sequence of vertices.
  • when removal of vertices is necessary, programmers must create a copy of the stroke explicitly before starting iteration over the vertices.

Correct code #1:

    for vertex in Stroke(stroke):
        if some condition holds:
            stroke.RemoveVertex(vertex)

Correct code #2:

    for vertex in list(stroke):
        if some condition holds:
            stroke.RemoveVertex(vertex)

Advertisements

3 Comments »

  1. Whoa, python control of stroke attributes in freestyle/blender. This is a very useful feature, thank you.

    Comment by 3D — December 1, 2008 @ 5:40 PM

  2. […] API syntax and remove the old SWIG/C++-based syntax from the API (see the blog entries on December 1, 2008 and on August 4, 2009 for more information on the syntactic improvements).  This means that […]

    Pingback by Weekly update March 29-April 4 « Freestyle integration into Blender — April 7, 2010 @ 12:40 AM

  3. […] remove the C++-style iteration syntax from the Python API.  In December 2008, we implemented the Python iterator protocol in Stroke and StrokeVertexIterator as a pilot case.  Initially, allowing Python-style iteration over vertices appeared a very good […]

    Pingback by Weekly update April 10-23 « Freestyle integration into Blender — May 23, 2010 @ 11:52 PM


RSS feed for comments on this post. TrackBack URI

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

Blog at WordPress.com.

%d bloggers like this: