Blender Python style guide
This is a living guide to help you write solid Python code for Blender.
It will help you write code that's easy to read, easy to review, and easy to maintain without compromising performance.
For tips on testing and debugging your code, and performances with Python, check these two official guides:
Code conventions for Blender Python
To work together on Free Software efficiently, we need to follow some conventions. This helps to make the code easy to read and to explore for everyone. This makes it easy for new contributors or fellow developers to fix bugs in your code.
Here's a complete class that follows all the conventions below, with some code removed so it's not too long to read:
Class names
Name classes as CATEGORY_TYPE_name
:
CATEGORY
is what the class works with or operates on. It can beOBJECT
,ACTION
for animation actions,ARMATURE
if it affects an armature,SEQUENCER
, etc.TYPE
is a two letters acronym that represents the nature of the class. You will useOT
for operators,MT
for menu templates, PT for panel templates, UL for UI lists, etc.name
is the name for your operator or UI element insnake_case
. Find a clear name that represents the action the class will perform or the UI element that it represents.
This naming scheme makes it easy to find features in the codebase. You can search for CATEGORY*operator_name
using tags or a search tool to find the source code of any operator listed in the program's keymaps.
In my code editor, searching code tags for SEQ _OT
, I instantly get the list of all of the sequencer's operators:
Some class name examples from Blender's source code:
5 techniques to write clean code
If you have quite a bit of programming experience already, you will notice that these tips are or build upon fundamental principles of Object-Oriented and Functional programming. They are general techniques that you can use to write great software. Software that:
Does what the users need and want
Is flexible
Mitigates risks
Avoid calling other operators
It feels natural to make new operators by calling lots of other operators that are included in blender. Whenever you can, you want to avoid that.
There are at least 3 reasons to avoid operators:
They add dependencies to your code, giving it more reasons to change
They require you to change and restore the user's selection, which can lead to unexpected bugs
They require you to mutate the scene's data, which can also lead to bugs or sometimes cause performance issues
Calling other operators create a dependency between your class and that operator, which is another class in the source code. Built-in operators can change between versions of blender, breaking your code.
Built-in operators often work with the user's selection or scene data in Blender to work. To use them in your code, you end up changing the user's selection and having to restore it at the end of your script. This is easy to forget, leading to unexpected bugs, and adding extra maintenance work for you.
Even though most built-in operators are written in fast C code, changes like moving the time cursor in the sequencer can force the view to refresh, slowing down your operator for the user.
Imagine you want to code an operator to offset all strips after the time cursor by 30 frames, ignoring locked strips. Using the built-in transform.seq_slide
operator, your code would look like this:
The code above stores, modifies, and then restores the user's selection. You can get the same result, without having to mess with the selection, like so:
In this case, it both simplifies the code and removes the dependencies on built-in operators.
The sorted
function sorts the sequences_to_move
by their start frame. We need to sort the sequences in this case to ensure that we will move them in the correct order. Otherwise, the sequences can end up moving to different channels. The lambda
feature creates an inline function that takes each sequence in sequences_to_move
as s
and returns its frame_final_start
.
If you find this code hard to read, you you can always create one or more functions to make your code more expressive:
Turning the line
Into:
Note: there is an operator in blender 2.80 to offset sequences after the time cursor. But it moves locked sequences like any other. That's why if you want to add that feature and avoid relying on this built-in operator, you have to code your own.
Tips to make your own code easier to read
The convention inside Blender is to use words common to several properties or methods as a prefix of the property or the function's name. For instance, the property names of sequences in the VSE related to climb on duration in frames all start with frame: frame_start
, frame_end
, and frame_duration
rather than start_frame
, end_frame
, and duration_frame
.
Even though the last three names are a bit more natural to read in English, when you are programming, it will be much easier to find all the frame related properties thanks to your code editor's autocomplete feature.
Last updated