Книга: Введение в написание скриптов на Питоне для Блендера 2.5x. Примеры кода
Модальный оператор
Модальный оператор
Следующий пример взят прямо из документации по API, как и последующие несколько примеров.
Модальный оператор определяет функцию Operator.modal
которая при запуске обрабатывает события, пока не вернёт 'FINISHED'
или 'CANCELLED'
. Grab (сдвиг), Rotate (вращение), Scale (масштабирование) и Fly-Mode (режим полёта) - примеры модальных операторов. Они особенно полезны для интерактивных инструментов, ваш оператор может иметь собственное состояние, в котором клавиши переключают опции работы оператора.
Когда вызывается оператор в этом примере, он добавляет модального обработчика к себе с помощью вызова context.window_manager.modal_handler_add(self)
. После этого активный объект продолжает перемещаться по плоскости XY, повторяя перемещения мыши. Для того, чтобы выйти, нажмите кнопку мыши или клавишу Esc.
Модальный метод обрабатывает три типа событий:
1. Перемещение мыши перемещает активный объект.
2. Нажатие ЛКМ для подтверждения и выхода в нормальный режим. Объект оставляется в своей новой позиции.
3. Нажатие ПКМ или клавиши Esc, чтобы отменить и выйти в нормальный режим. Объект возвращается в свою первоначальную позицию.
Важно, чтобы был некоторый способ выходить в нормальный режим. Если функция modal() всегда возвращает 'RUNNING_MODAL', скрипт войдёт в бесконечный цикл, и Вам придётся перезапускать Блендер.
Модальный оператор определяет два специальных метода с именами __init()__
и __del()__
, которые вызываются, когда модальная операция начинается и прекращается, соответственно.
Запустите скрипт. Активный объект перемещается по плоскости XY при перемещении мыши. Скрипт также создает панель с кнопкой, нажатием на которую Вы также можете выполнить модальный оператор.
#----------------------------------------------------------
# File modal.py
# from API documentation
#----------------------------------------------------------
import bpy
class MyModalOperator(bpy.types.Operator):
bl_idname = "mine.modal_op"
bl_label = "Move in XY plane"
def __init__(self):
print("Start moving")
def __del__(self):
print("Moved from (%d %d) to (%d %d)" %
(self.init_x, self.init_y, self.x, self.y))
def execute(self, context):
context.object.location.x = self.x / 100.0
context.object.location.y = self.y / 100.0
def modal(self, context, event):
if event.type == 'MOUSEMOVE': # Применение
self.x = event.mouse_x
self.y = event.mouse_y
self.execute(context)
elif event.type == 'LEFTMOUSE': # Подтверждение
return {'FINISHED'}
elif event.type in ('RIGHTMOUSE', 'ESC'): # Отмена
return {'CANCELLED'}
return {'RUNNING_MODAL'}
def invoke(self, context, event):
self.x = event.mouse_x
self.y = event.mouse_y
self.init_x = self.x
self.init_y = self.y
self.execute(context)
print(context.window_manager.modal_handler_add(self))
return {'RUNNING_MODAL'}
#
# Панель в районе tools
#
class MyModalPanel(bpy.types.Panel):
bl_label = "My modal operator"
bl_space_type = "VIEW_3D"
bl_region_type = "TOOLS"
def draw(self, context):
self.layout.operator("mine.modal_op")
# Регистрация
bpy.utils.register_module(__name__)
# Автоматически перемещает активный объект при запуске
bpy.ops.mine.modal_op('INVOKE_DEFAULT')
- Панели и кнопки
- Планировка панели и несколько аргументов
- Панель свойств
- Использование свойств сцены для сохранения информации
- Опрос (Polling)
- Динамическое выпадающее меню
- Объявление оператора и добавление его в меню
- Модальный оператор
- Invoke (вызов) против execute (выполнения)
- Всплывающий диалог
- Диалоговое окно ошибки
- Арифметические операторы
- 1.2.4. Операторы и приоритеты
- Условные операторы
- 1. Оператор Select – базовый оператор языка структурированных запросов
- Поразрядные операторы
- Оператор цикла foreach
- Логические операторы
- Оператор goto
- A7.11. Оператор побитового И
- Использование операторов if для выбора вариантов
- 2.1.3. Оператор варианта (переключатель)
- Оператор цикла for