Blender Documentation: Last modified September 01 2003 S68
<<< Previous |  | Next >>>

# Python Scripting

Blender has a very powerful yet often overlooked feature. It exhibits an internal full fledged Python interpreter.

This allows any user to add functionalities by writing a Python script. Python is an interpreted, interactive, object-oriented programming language. It incorporates modules, exceptions, dynamic typing, very high level dynamic data types, and classes. Python combines remarkable power with very clear syntax. It was expressely designed to be usable as an extension language for applications that need a programmable interface, and this is why Blender uses it.

Blender has a "Text window" among its windows types accessible via the button of the window type menu or via SHIFT F11.

The newley opened Text window is grey and empty, with a very simple toolbar (Figure 1). From left to right there are the standard Window type selection button and the fullscreen button, followed by a toggle button which shows/hides the line numbers for the text and the regular select button.

Figure 1. Text Toolbar.

The select button ( ) allows to select which Text buffer is to be displayed, as well as allowing to create a new buffer or loading a text file.

Once a text buffer is in the Text window, this behaves as a very simple text editor. Typing on the keyboard produces text in the text buffer. As usual pressing, LMB dragging and releasing LMB selects text. The following keyboard commands apply:

- ALT C or CTRL C - Copy the marked text into a buffer;

- ALT X or CTRL X - Cut out the marked text into a buffer;

- ALT V or CTRL V - Paste the text from buffer to the cursor in the textwindow;

- ALT S - Saves the text as a textfile, a FileWindow appears;

- ALT O - Loads a text, a FileWindow appears;

- SHIFT ALT F or RMB - Pops up the Filemenu for the TextWindow;

- ALT J - Pops up a NumButton where you can specify a linenumber the cursor will jump to;

- ALT P - Executes the text as a Python script;

- ALT U or CTRL U - Undo;

- ALT R or CTRL R - Redo;

- ALT M - Converts the content of the text window into 3D text (max 100 chars);

Blender's cut/copy/paste buffer is separate from WIndow's clipboard. So normally you cannot cut/paste/copy out from/into Blender. To access your Windows clipboard use CTRL ALT C CTRL ALT V

To delete a text buffer just press the 'X' button next to the buffer's name, just as you do for materials, etc.

The most notable keystroke is ALT P which makes the content of the buffer being parsed by the internal Python interpreter built into Blender.

The next section will present an example of Python scripting. Before going on it is worth noticing that Blender comes with only the bare Python interpreter built in, and with a few Blender-specific modules, those described in the Section called API Reference.

to have access to the standard Python modules you need a complete working python install. You can download this from http://www.python.org. Be sure to check on http://www.blender.org which is the exact Python version which was built into BLender to prevent compatibility issues.

Blender must also be made aware of where this full Python installation is. This is done by defining a `PYTHONPATH` environment variable.

Setting `PYTHONPATH` on Win95,98,Me. Once you have installed Python in, say, `C:\PYTHON22` you must open the file `C:\AUTOEXEC.BAT` with your favorite text editor, add a line:

    SET PYTHONPATH=C:\PYTHON22;C:\PYTHON22\DLLS;C:\PYTHON22\LIB;C:\PYTHON22\LIB\LIB-TK

and reboot the system.

Setting `PYTHONPATH` on WinNT,2000,XP. Once you have installed Python in, say, `C:\PYTHON22` Go on the "My Computer" Icon on the desctop, RMB and select `Properties`. Select the `Advanced` tab and press the `Environment Variables` button.

Below the System Variables box, (the second box), hit `New`. If you are not an administrator you might be unable to do that. In this case hit `New` in the upper box.

Now, in the Variable Name box, type PYTHONPATH, in the Variable Value box, type:

    SET PYTHONPATH=C:\PYTHON22;C:\PYTHON22\DLLS;C:\PYTHON22\LIB;C:\PYTHON22\LIB\LIB-TK

Hit OK repeatedly to exit from all dialogs. You may or may not have to reboot, dependingo on the OS.

Setting `PYTHONPATH` on Linux and other UNIXes. Normally you will have Python already there. if not, install. You will have to discover where it is. This is easy, yust start a python interactive shell opening a shell and typing `python` in there. Type the following commands:

    >>> import sys
    >>> print sys.path

and note down the output, it should look like

    ['', '/usr/local/lib/python2.2', '/usr/local/lib/python2.2
    /plat-linux2', '/usr/local/lib/python2.0/lib-tk', '/usr/lo
    cal/lib/python2.0/lib-dynload', '/usr/local/lib/python2.0/
    site-packages']

Add this to your favourite `rc` file as an evironment variable setting. For example, add in your `.bashrc` the line

    export PYTHONPATH=/usr/local/lib/python2.2:/usr/local/lib/
    python2.2/plat-linux2:/usr/local/lib/python2.2/lib-tk:/usr
    /local/lib/python2.2/lib-dynload:/usr/local/lib/python2.0/
    site-packages

all on a single line. Open a new login shell, or logoff and login again.

| Other usages for the Text window

The text window is handy also when you want to share your .blend files with the community or with your friends. A Text window can be used to write in a README text explaining the contents of your blender file. Much more handy that having it on a separate application. Be sure to keep it visible when saving!

If you are sharing the file with the community and you want to share it under some licence you can write the licence in a text window.

# A working Python example

Now that you've seen that Blender is extensible via Python scripting and that you've got the basics of script handling and how to run a script, and before smashing your brain with the full python API reference contained in next section let's have a look to a quick and dirty working example.

We will present a tiny script to produce polygons. This indeed duplicates somewhat the ADD>>Mesh>>Circle menu entry, but will create 'filled' polygons, not just the outline.

To make the script simple yet complete it will exhibit a Graphical User Interface (GUI) completely written via Blender's API.

## Headers, importing modules and globals.

The first 32 lines of code are reported in Example 1.

Example 1. Script header

    001 ######################################################
    002 #
    003 # Demo Script for Blender Manual
    004 #
    005 ###################################################S68
    006 # This script generates polygons. It is quite useless
    007 # since you can do polygons with ADD->Mesh->Circle
    008 # but it is a nice complete script example, and the
    009 # polygons are 'filled'
    010 ######################################################
    011
    012 ######################################################
    013 # Importing modules
    014 ######################################################
    015
    016 import Blender
    017 from Blender import NMesh
    018 from Blender.BGL import *
    019 from Blender.Draw import *
    020
    021 import math
    022 from math import *
    023
    024 # Polygon Parameters
    025 T_NumberOfSides = Create(3)
    026 T_Radius        = Create(1.0)
    027
    028 # Events
    029 EVENT_NOEVENT = 1
    030 EVENT_DRAW    = 2
    031 EVENT_EXIT    = 3
    032

After the necessary comments with the description of what the script does there is (lines 016-022) the importing of Python modules.

`Blender` is the main Blender Python API module. `NMesh` is the module providing access to Blender's meshes, while `BGL` and `Draw` give access to the OpenGL constants and functions and to Blender's windowing interface, respectively. The `math` module is Python's mathematical module.

The polygons are defined via the number of sides they have and their radius. These parameters have values which must be defined by the user via the GUI hence lines (025-026) creates two 'generic button' objects, with their default starting value.

Finally, the GUI objects works witha and generates events. Events identifier are integers left to the user to define. It is usually a good practice to define mnemonic names for events, as it is done here in lines (029-031).

## Drawing the GUI.

The code responsible for drawing the code should reside in a `draw` function (Example 2).

Example 2. GUI drawing

    033 ######################################################
    034 # GUI drawing
    035 ######################################################
    036 def draw():
    037 	global T_NumberOfSides
    038 	global T_Radius
    039 	global EVENT_NOEVENT,EVENT_DRAW,EVENT_EXIT
    040
    041 	########## Titles
    042 	glClear(GL_COLOR_BUFFER_BIT)
    043 	glRasterPos2d(8, 103)
    044 	Text("Demo Polygon Script")
    045
    046 	######### Parameters GUI Buttons
    047 	glRasterPos2d(8, 83)
    048 	Text("Parameters:")
    049 	T_NumberOfSides = Number("No. of sides: ", EVENT_NOEVENT, 10, 55, 210, 18,
    050                     T_NumberOfSides.val, 3, 20, "Number of sides of out polygon");
    051 	T_Radius        = Slider("Radius: ", EVENT_NOEVENT, 10, 35, 210, 18,
    052                     T_Radius.val, 0.001, 20.0, 1, "Radius of the polygon");
    053
    054 	######### Draw and Exit Buttons
    055 	Button("Draw",EVENT_DRAW , 10, 10, 80, 18)
    056 	Button("Exit",EVENT_EXIT , 140, 10, 80, 18)
    057

Lines (037-039) merely grant access to global data. The real interesting stuff starts from lines (042-044). The OpenGL window is initialized, and the current position set to x=8, y=103. The origin of this reference is the lower left corner of the script window. Then the title `Demo Polygon Script` is printed.

A further string is written (lines 047-048), then the input buttons for the parameters are created. The first (lines 049-050) is a NumButton, exactly alike those in the varouis Blender ButtonWindows. For the meaning of all the parameters pleas refer to the API reference. Basically ther eis the button label, the event generated by the button, its location (x,y) and its dimensions (width, height), its value, the minimum and maximum allowable values and a text string which willl appear as an help while hoovering on the button.

Lines (051-052) defines a slider, with a very similar sintax. Lines (055-056) finally creates a `Draw` butto which will create the polygon and an `Exit` button.

## Managing Events.

The GUI is not drawn, and would not work, untill a proper event handler is written and registered (Example 3).

Example 3. Handling events

    058 def event(evt, val):
    059 	if (evt == QKEY and not val):
    060 		Exit()
    061
    062 def bevent(evt):
    063 	global T_NumberOfSides
    064 	global T_Radius
    065 	global EVENT_NOEVENT,EVENT_DRAW,EVENT_EXIT
    066
    067 	######### Manages GUI events
    068 	if (evt == EVENT_EXIT):
    069 		Exit()
    070 	elif (evt== EVENT_DRAW):
    071 		Polygon(T_NumberOfSides.val, T_Radius.val)
    072  		Blender.Redraw()
    073
    074 Register(draw, event, bevent)
    075

Lines (058-060) defines the keyboard event handler, here responding to the QKEY with a plain `Exit()` call.

More interesting are lines (062-072), in charge of managing the GUI events. Every time a GUI button is used this function is called, with the event number defined within the button as a parameter. The core of this function is ence a "select" structure executing different codes accordingly to the event number.

As a last call, the `Register` function is invoked. This effectively draws the GUI and starts the event capturing cycle.

## Mesh handling

Finally, Example 4 shows the main function, the one creating the polygon. It is a rather simple mesh editing, but shows many important points of the Blender's internal data structure

Example 4. Script header

    076 ######################################################
    077 # Main Body
    078 ######################################################
    079 def Polygon(NumberOfSides,Radius):
    080
    081	######### Creates a new mesh
    082	poly = NMesh.GetRaw()
    083
    084	#########Populates it of vertices
    085	for i in range(0,NumberOfSides):
    086	  phi = 3.141592653589 * 2 * i / NumberOfSides
    087	  x = Radius * cos(phi)
    088	  y = Radius * sin(phi)
    089	  z = 0
    090
    091	  v = NMesh.Vert(x,y,z)
    092	  poly.verts.append(v)
    093
    094	#########Adds a new vertex to the center
    095	v = NMesh.Vert(0.,0.,0.)
    096	poly.verts.append(v)
    097
    098	#########Connects the vertices to form faces
    099	for i in range(0,NumberOfSides):
    100		f = NMesh.Face()
    101		f.v.append(poly.verts[i])
    102		f.v.append(poly.verts[(i+1)%NumberOfSides])
    103		f.v.append(poly.verts[NumberOfSides])
    104		poly.faces.append(f)
    105
    106	#########Creates a new Object with the new Mesh
    107	polyObj = NMesh.PutRaw(poly)
    108
    109	Blender.Redraw()

The first important line here is number (082). Here a new mesh object, `poly` is created. The mesh object is constituted of a list of vertices and a list of faces, plus some other interesting stuff. For our purpouses the vertices and faces lists are what we need.

Of course the newely created mesh is empty. The first cycle (lines 085-092) computes the x,y,z location of the `NumberOfSides` vertices needed to define the polygon. Being a flat figure it is z=0 for all.

Line (091) call the `NMesh` method `Vert` to create a new vertex object of coords (x,y,z). Such an object is then appended (line 096) in the `poly` Mesh `verts` list.

Finally (lines 095-096) a last vertex is added in the center.

Lines (099-104) now connects these vertices to make faces. It is not required to create all vertices beforehand and then faces. You can safely create a new face as soon as all its vertices are there.

Line (100) creates a new face object. A face object has its own list of vertices `v` (up to 4) defining it. Lines (101-103) appends three vertices to the originally empty `f.v` list. The vertices are two subsequent vertices of the polygon and the central vertex. These vertices must be taken from the Mesh `verts` list. finally line (104) appends the newly created face to the `faces` list of our `poly` mesh.

## Conclusions

If you create a `polygon.py` file containing the above described code and load it into a Blender text window as you learned in the previous section and press ALT P in that window to run it you will see the script disappearing and the window turn grey. In the lower left corner the GUI will be drawn (Figure 2 )

Figure 2. The GUI of our example.

By selecting, for example, 5 vertices and a radius 0.5, and by pressing the `Draw` button a pentagon will appear on the xy plane of the 3D window (Figure 3 )

Figure 3. The result of our example script.

<<< Previous | Home | Next >>>
Constraint Types | Up | API Reference