หมุนวัตถุไปที่มุมมองกล้อง

Aug 20 2020

ฉันพยายามทำให้สิ่งนี้ชัดเจนที่สุด:

จุดเริ่ม

ฉันวางวัตถุที่กึ่งกลาง (0,0,0) ของฉาก จากนั้นฉันวางกล้องโดยกำหนดรัศมีการแก้ไขบนซีกโลกรอบ ๆ วัตถุ (และใช้ข้อ จำกัด เพื่อให้มันมองไปที่วัตถุเสมอ) และแสดงภาพ ฉันส่งออกวัตถุเป็น. stl ด้วย y-up และ minus-z-forward เพื่อเปิดด้วยไลบรารีอื่นที่ใช้รูปแบบที่แตกต่างกันนี้

ปัญหา

ฉันต้องการหมุนวัตถุในลักษณะที่สอดคล้องกับมุมมองของภาพที่แสดง

วิธีการ

รู้จักมุมของมุมราบและมุมเงย ดังนั้นฉันจึงคำนวณเมทริกซ์การหมุนโดยให้สองมุม (ฉันต้องการเมทริกซ์การหมุนที่เป็นเนื้อเดียวกันดังนั้นจึงผนวก 0s และ 1)

def angles_to_matrix(phi, theta):
    # phi describes the azimuth
    azi = phi
    # theta describes the inclination angle, thus:
    ele = radians(90) - theta
    rol = 0
    
    e1 = cos(rol) * cos(azi) - sin(rol) * cos(ele) * sin(azi)
    e2 = sin(rol) * cos(azi) + cos(rol) * cos(ele) * sin(azi)
    e3 = sin(ele) * sin(azi)
    e4 = -cos(rol) * sin(azi) - sin(rol) * cos(ele) * cos(azi)
    e5 = -sin(rol) * sin(azi) + cos(rol) * cos(ele) * cos(azi)
    e6 = sin(ele) * cos(azi)
    e7 = sin(rol) * sin(ele)
    e8 = -cos(rol) * sin(ele)
    e9 = cos(ele)
    
    return np.array(((e1, e2, e3, 0), (e4, e5, e6, 0), (e7, e8, e9,0 ), (0, 0, 0, 1)))

การหมุนดูไม่ถูกต้อง & ฉันรู้สึกว่าอาจมีหลายสิ่งผิดพลาด:

  • ฉันพลาดอะไรเกี่ยวกับการเปลี่ยนแนวแกนหรือไม่?
  • เป็นไปได้หรือไม่ที่จะใช้มุมเดียวกันในการคำนวณพิกัดทรงกลมเพื่อคำนวณการหมุนของวัตถุ?

คุณมีความคิดหรือไม่?

คำตอบ

1 batFINGER Aug 25 2020 at 21:33

จัดแนววัตถุให้เข้ากับกล้อง

สิ่งนี้จะให้ผลลัพธ์เช่นเดียวกับการเพิ่มวัตถุในมุมมองกล้องและการใช้ ALIGN to VIEW

โดยค่าเริ่มต้นวัตถุเครื่องปั่นจะหันหน้าไปทาง -Y และมี Z ขึ้น ในทางกลับกันกล้องจะมองลง -Z โดย Y ขึ้น

สามารถย่อยสลายเมทริกซ์ของวัตถุให้เป็นตำแหน่งการหมุนและมาตราส่วนแล้วจัดองค์ประกอบใหม่

ในกรณีนี้ให้รับส่วนการหมุนของโลกเมทริกซ์ของกล้องเปลี่ยนเป็น -Y ไปข้างหน้าและ Z ขึ้นไปจากนั้นประกอบเข้าไปในวัตถุด้วยมาตราส่วนดั้งเดิมและการแปล

import bpy
from mathutils import Vector, Matrix
from bpy import context
from bpy_extras.io_utils import axis_conversion

scene = context.scene
cam_ob = scene.camera
ob = context.object

A = axis_conversion(
        from_forward='Z',
        from_up='-Y',
        to_forward='Y',
        to_up='Z').to_4x4()

loc, rot, scale = cam_ob.matrix_world.decompose()

ob.matrix_world = (
    Matrix.Translation(ob.matrix_world.to_translation()) @
   (rot.to_matrix().to_4x4() @ A) @
    Matrix.Diagonal(ob.matrix_world.to_scale()).to_4x4()
    )