[PYTHON] Two prototypes of Blender camera scripts

Register as an article on the 23rd of ADVENTAR's Blender Advent Calendar 2020 https://adventar.org/calendars/5212

There was a topic that I wanted a function to operate the camera to use it for manga sketches in chat. I tried to make a prototype of the function. Both are prototypes and their functions are close to memo writing.

Shift the camera so that the desired position is centered

Change the value of camera shift (a function that changes the display as if it was translated while keeping the camera view) A script to make it easier

Set the shift value so that the 3D cursor position seen in the camera view is the center. image.png

CameraShift/py


import bpy
import math
from mathutils import Vector, Matrix

scene = bpy.context.scene
camera = scene.camera
camera_data = camera.data

matrix = camera.matrix_world
camera_angle = camera_data.angle
print(camera_angle)


target_location = scene.cursor.location - camera.location
loc = [email protected]_world

print(loc)

x_tan = loc[0]/loc[2]
y_tan = loc[1]/loc[2]
angle_tan = math.tan(camera_angle/2)
print(angle_tan)
camera_data.shift_x = -x_tan /(2*angle_tan)
camera_data.shift_y = -y_tan /(2*angle_tan)

Conversely, if you want to move the center of the camera to the 3D cursor position, With the shift of 0, the last two lines

camera_data.shift_x = x_tan /(2*angle_tan)
camera_data.shift_y = y_tan /(2*angle_tan)

Just do the reverse of the sign From the state where the shift has already been set, a little more adjustment will be required.

Set the camera to fit a part of the image

This script is used when you want to create a rendered image that fits one frame of a manga.

Keep the sketch of the camera and the image displayed in the image editor the same By marking the area you want to fit in the camera with the annotation on the image editor Specifies the display range and rendering resolution. image.png

GpenCrip.py


import bpy
scene = bpy.context.scene
#strokes = bpy.context.annotation_data.layers.active.active_frame.strokes
strokes = bpy.data.grease_pencils[0].layers[0].active_frame.strokes
#Annotations are filtered because some are used for 3D views and some are used for 3D views.
strokes_2d = [ s for s in strokes if s.display_mode == '2DSPACE']
x_list = []
y_list = []
for stroke in strokes_2d:
    x_list += [pos.co[0] for pos in stroke.points]
    y_list += [pos.co[1] for pos in stroke.points]

bbox = [min(x_list),min(y_list), max(x_list), max(y_list)]
#Get information on camera sketch images
camera = scene.camera
bg_image = camera.data.background_images[0]
bg_size = bg_image.image.size

#Setting the display range of the sketch
bg_image.frame_method = 'CROP'
crop_size = [(bbox[2] -bbox[0])*bg_size[0], (bbox[3] -bbox[1])*bg_size[1]]
#Cut out the background trim by putting it in the frame based on the larger one compared to the ratio of the background image.
if bg_size[0] * crop_size[0] > bg_size[1] * crop_size[1]:
    bg_scale = bg_size[0] / crop_size[0]
else:
    bg_scale = bg_size[1] / crop_size[1]
bg_image.scale = bg_scale
#Set the center position of the sketch
bg_image.offset = ((bbox[0] + bbox[2] -1) *-0.5 *bg_scale, (bbox[1]+ bbox[3] -1) *-0.5 *bg_scale) 
#Rendering image size settings
scene.render.resolution_x = crop_size[0]
scene.render.resolution_y = crop_size[1]

Since it is still a prototype, only the first 1 annotation can be obtained. Although it is troublesome to prepare the sketch and the image to be displayed in the image editor. I hope it helps you in some way.

Recommended Posts

Two prototypes of Blender camera scripts