|
|
Для работы с Python в Blender существует Python консоль для ввода команд. Данная консоль может быть вызвана с помощью комбинации shift+F4.
В данной консоли можно вводить команды на языке Python. После ввода комманды, результат выполнения будет выведен сразу после окончания ввода команды. Примечание: Перед выполнением задания, необходимо знать точный и полный путь до файла с данными. |
Пример программы
# Считываем бибилиотеки относящиеся к маетматическим функциям и процедурам
import itertools
import math
# Очищаем пространственную сцену от объектов
for mesh in bpy.data.meshes:
bpy.data.meshes.remove(mesh)
# Очищаем пространственную сцену от камер
for cam in bpy.data.cameras:
bpy.data.cameras.remove(cam)
# Sourcing
data_file_path = "data/c20.txt" # Путь до файла с данными
data_array = []
with open(data_file_path) as data_file: # Считываем данные из файла
for line in data_file:
data_array.append([float(number) for number in line.split()])
# Filtering
filtered_data_array = data_array # Filtering пуст
# Mapping
sphere_radius = 0.1 # Задаем радиус сфер
minimal_distance = 1.5 # Задаем минимальное расстояние для цилиндров
sphere_material = bpy.data.materials.new(name="SphereMaterial")
sphere_material.diffuse_color = [0.5, 0.9, 0.3, 1] # Задаем цвет сфер
for point in filtered_data_array:
# Создаем сферу
bpy.ops.mesh.primitive_uv_sphere_add(radius=sphere_radius, location=point)
sphere = bpy.context.object
# Добавляем материал для сферы
sphere.data.materials.append(sphere_material)
cylinder_radius = sphere_radius / 2 # Задаем радиус цилиндра
cylinder_material = bpy.data.materials.new(name="SphereMaterial")
cylinder_material.diffuse_color = [1, 1, 1, 1] # Задаем цвет цилиндров
for start, end in itertools.combinations(filtered_data_array, 2):
# Считаем расстояние между точками
distance = math.dist(start, end)
if distance < minimal_distance:
diff = [start[i] - end[i] for i in range(3)]
middle = [(start[i] + end[i]) / 2 for i in range(3)]
# Создаем цилиндр
bpy.ops.mesh.primitive_cylinder_add(
radius=cylinder_radius, depth=distance, location=middle
)
cylinder = bpy.context.object
# Поварачиваем цилиндр
cylinder.rotation_euler[1] = math.acos(diff[2] / distance)
cylinder.rotation_euler[2] = math.atan2(diff[1], diff[0])
cylinder.data.materials.append(cylinder_material)
# Rendering
camera_location = [5, 5, 5]
camera_target = [0, 0, 0]
# Задаем вектор для камеры
camera_view_vector = [camera_target[i] - camera_location[i] for i in range(3)]
# Создаем камеру
camera = bpy.data.objects.new("Camera", bpy.data.cameras.new("Camera"))
# Помещаем и поварачиваем камеру
camera.location = camera_location
camera.rotation_euler = Vector(camera_view_vector).to_track_quat('-Z', 'Y').to_euler()
# Помещаем камеру на сцену и выбираем её в качестве активной камеры
bpy.context.scene.collection.objects.link(camera)
bpy.context.scene.camera = camera
for area in bpy.context.screen.areas:
if area.type == "VIEW_3D":
area.spaces.active.region_3d.view_perspective = "CAMERA"
break
|
|
Программа вводится и выполняется по частям. |
Часть 1 SourcingВводим текст отвечающий за Sourcing. Большая часть команд в Python не возвращает результатов, видимых в консоли. Если ввести в консоли переменную, содержащую данные, то можно увидеть следующее: >>> data_array [[-1.219094, -0.6134905, 1.568064], [-1.219048, 0.7947012, 1.568227], [0.1202303, 1.229807, 1.568158], [0.9479346, 0.09052898, 1.567944], [0.1201712, -1.048725, 1.567888], [-1.818241, -1.048416, 0.3701912], [-2.188474, 0.09094238, -0.369963], [-1.818136, 1.23007, 0.3704882], [-0.8492718, -1.752463, -0.3703749], [0.3487037, -1.752652, 0.3698422], [-0.8491096, 1.934269, -0.3698732], [0.3488672, 1.934088, 0.3703492], [1.317876, 1.230073, -0.370188], [1.688112, 0.09069566, 0.3699504], [1.317813, -1.048485, -0.3704498], [-1.448331, 0.091057, -1.567983], [-0.6205603, 1.230299, -1.567894], [0.7187238, 0.7951232, -1.568042], [0.7187231, -0.6130653, -1.568167], [-0.620568, -1.048182, -1.568168]] Что означает что данные были успешно считаны из файла |
Часть 2 FilteringПостольку поскольку filtering пуст, данная часть не меняет данные. Если ввести в консоли переменную, отвечающую за отфильтрованные данные, чтобы убедится что ничего не изменилось: >>> filtered_data_array [[-1.219094, -0.6134905, 1.568064], [-1.219048, 0.7947012, 1.568227], [0.1202303, 1.229807, 1.568158], [0.9479346, 0.09052898, 1.567944], [0.1201712, -1.048725, 1.567888], [-1.818241, -1.048416, 0.3701912], [-2.188474, 0.09094238, -0.369963], [-1.818136, 1.23007, 0.3704882], [-0.8492718, -1.752463, -0.3703749], [0.3487037, -1.752652, 0.3698422], [-0.8491096, 1.934269, -0.3698732], [0.3488672, 1.934088, 0.3703492], [1.317876, 1.230073, -0.370188], [1.688112, 0.09069566, 0.3699504], [1.317813, -1.048485, -0.3704498], [-1.448331, 0.091057, -1.567983], [-0.6205603, 1.230299, -1.567894], [0.7187238, 0.7951232, -1.568042], [0.7187231, -0.6130653, -1.568167], [-0.620568, -1.048182, -1.568168]] |
Часть 3 MappingЗапускаем часть отвечаю за Mapping. После создания каждой сферы и каждого цилиндра, Blender выведет следующее сообщение в консоль: {'FINISHED'} В окне отвечающем за пространственную сцену, мы видим текующее проекционное изображение пространстенной сцены с созданными сферами и цилиндрами.
|
Часть 4 RenderingЗапускаем часть отвечаю за Rendering. После задания и активации камеры, мы видим проекционное графическое изображение, полученное с помощью созданной нами камеры.
|
Часть 5 BackloopЕсли аналитик хочет поменять цвет цилиндров, можно ввести следующую команду для изменения цвета цилиндров с белого на красный и сделать их слегка прозрачными: cylinder_material.diffuse_color = [0.9,0,0,0.8]
|
|
Мы рекомендуем ознакомится с основами Python на официальном сайте, а так же с основами использования Blender библиотек. |