【问题标题】:Try using Equirectangular Projection to convert 2D coordinates to 3D coordinates. But failed. What am I doing wrong?尝试使用 Equirectangular Projection 将 2D 坐标转换为 3D 坐标。但失败了。我究竟做错了什么?
【发布时间】:2018-08-12 12:12:21
【问题描述】:

目前,我正在 Unity 中制作 360 度视频应用。我通过使用 equirectangular 投影的Unity Skybox Panoramic shader 成功制作了要渲染的视频。现在我正在尝试通过给定的一些 2D 点在视频上设置一些按钮。 2D 点系统有点棘手,并且与笛卡尔系统不同(我的老板要求它......)。 x 轴的范围是从-90(顶部)到 90(底部),并用作垂直轴。 y轴的范围是-180到180,用作横轴。现在关于计算 3D 坐标的话题,我阅读了 equirectangular 投影的wiki page 并看到了方程式。我假设 φ1 和 λ0 为零,因为没有旋转?所以λ(经度)和φ(纬度)在计算中只是y(横坐标)和-x(纵坐标)。由于经度和纬度也只是球坐标中的 θ 和 φ,因此我使用这个 C# 程序计算坐标:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class CreateButtons : MonoBehaviour {

    public GameObject testObject;
    public Vector2 generatePositionStart;
    public Vector2 generatePositionEnd;
    public float radius = 50f;
    const float LONPERPIXEL = 3840f / 360f;

    // Use this for initialization
    void Start () {
        Vector3 pointS = GetPoint (radius, generatePositionStart.y * LONPERPIXEL, -generatePositionStart.x * LONPERPIXEL);
        GameObject start = Instantiate (testObject, pointS, Quaternion.identity) as GameObject;
        start.name = "Start";
        Vector3 pointE = GetPoint (radius, generatePositionEnd.y * LONPERPIXEL, -generatePositionEnd.x * LONPERPIXEL);
        GameObject end = Instantiate (testObject, pointE, Quaternion.identity) as GameObject;
        end.name = "End";
    }

    Vector3 GetPoint (float rho, float theta, float phi) {
        float x = rho * Mathf.Sin (theta) * Mathf.Cos (phi);
        float y = rho * Mathf.Sin (theta) * Mathf.Sin (phi);
        float z = rho * Mathf.Cos (theta);
        return new Vector3 (x, y, z);
    }
}

程序将计算按钮的两个二维坐标(左上角和右下角)。然后在 3D 位置上生成两个球体。但是,计算的 3D 坐标不在正确的位置上。我是不是做错了什么?

P.S.:我发现了另一个方程,它说它是一个逆映射方程。我试过了,但仍然有错误的位置。方程式如下所示:

float x = rho * Mathf.Cos (theta) * Mathf.Cos (phi);
float y = rho * Mathf.Sin (theta) * Mathf.Cos (phi);
float z = rho * Mathf.Sin (theta);

【问题讨论】:

    标签: c# unity3d projection 360-degrees 360-panorama


    【解决方案1】:

    现在,我要自己回答了。这段代码有几个问题:

    1. 转换不需要LONPERPIXEL
    2. Unity CosSin 函数使用弧度,因此 theta 和 phi 必须乘以 Mathf.Deg2Rad
    3. GetPoint() 中的方程式完全错误。

    所以这里是正确的代码:

    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;
    
    public class CreateButtons : MonoBehaviour {
    
        public GameObject testObject;
        public Vector2 generatePositionStart;
        public Vector2 generatePositionEnd;
        public float radius = 50f;
    
        // Use this for initialization
        void Start () {
            Vector3 pointS = GetPoint (radius, generatePositionStart.y * Mathf.Deg2Rad, -generatePositionStart.x * Mathf.Deg2Rad);
            GameObject start = Instantiate (testObject, pointS, Quaternion.identity) as GameObject;
            start.name = "Start";
            Vector3 pointE = GetPoint (radius, generatePositionEnd.y * Mathf.Deg2Rad, -generatePositionEnd.x * Mathf.Deg2Rad);
            GameObject end = Instantiate (testObject, pointE, Quaternion.identity) as GameObject;
            end.name = "End";
        }
    
        // Update is called once per frame
        void Update () {
    
        }
    
        Vector3 GetPoint (float rho, float theta, float phi) {
            float x = rho * Mathf.Sin (theta) * Mathf.Cos (phi);
            float y = rho * Mathf.Sin (phi);
            float z = rho * Mathf.Cos (theta) * Mathf.Cos (phi);
            return new Vector3 (x, y, z);
        }
    }
    

    【讨论】:

      猜你喜欢
      • 2018-05-25
      • 2021-05-05
      • 1970-01-01
      • 1970-01-01
      • 2015-01-01
      • 2015-06-29
      • 2014-06-12
      • 2015-12-02
      • 2012-03-06
      相关资源
      最近更新 更多