加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 编程开发 > Python > 正文

python – 使用90°滚动转换并重新映射equirectangular图像

发布时间:2020-12-16 22:51:53 所属栏目:Python 来源:网络整理
导读:我必须将一个equirectangular图像转换并重新映射到另一个90°滚动的equirectangular图像. 我用Pano2VR做了. 问题是我必须从服务器端以编程方式执行此操作.所以我不能使用G.U.I.去做吧. 首先,我将我的研究定位于imagemagick.我尝试了Fred ImageMagick scripts

我必须将一个equirectangular图像转换并重新映射到另一个90°滚动的equirectangular图像.

我用Pano2VR做了.

问题是我必须从服务器端以编程方式执行此操作.所以我不能使用G.U.I.去做吧.

首先,我将我的研究定位于imagemagick.我尝试了Fred ImageMagick scripts,但找不到任何人做我想做的事.而且,与Pano2VR相比,图像的处理时间显得非常长.

我将我的调查指导到OpenCV和libgnomonic.这是目前最有趣的方式.这个库允许用户转换投影(equirectangular到直线,反之亦然)或make equirectangular mapping transformation.我玩Norama-suite,包含一些处理库的脚本.例如,我想将直线图像转换为equirectangular,但输出只是一个黑色背景图像(为什么?我找不到答案).

但是,第二个链接可以解决我的问题.我有这个图像:

我想把它转换成这个图像

好吧,我对C一点也不舒服.
我想我应该使用这两个文件:

> https://www.github.com/FoxelSA/libgnomonic/blob/master/src/gnomonic-transform.h
> https://www.github.com/FoxelSA/libgnomonic/blob/master/src/gnomonic-transform.c

但我不知道怎么做.最重要的是,我想了解.

我是正确的吗?在第一张图片上应用了哪些转换?有没有办法用python或bash脚本来做?

好的,谢谢你的帮助.

**在python中编辑C的转换**
以下代码不起作用并返回和IndexError.
但是我试图抓住并传递异常,图像的第一个右侧部分似乎没有改变.

import math
from PIL import Image

img = Image.open("img1.jpg")
img = img.convert('RGB')
pixel = img.load()
width,height = img.size

img2 = img.copy()
for y in xrange(height):
    for x in xrange(width):
        xx = 2*(y+0.5) / width - 1.0
        yy = 2*(y+0.5)/ height - 1.0
        lng = math.pi * xx
        lat = 0.5 * math.pi * yy

        # NOTE!  These axes are transposed because that's what the question is about
        Z = math.cos(lat) * math.cos(lng)  # normally X
        Y = math.cos(lat) * math.sin(lng)  # normally Y
        X = -math.sin(lat)                 # normally -Z
        D = math.sqrt(X*X+Y*Y)

        lat = math.atan2(Z,D)             # ? normally lat = math.asin(Z)
        lng = math.atan2(Y,X)

        #ix and iy must be integers
        ix = int((0.5 * lng / math.pi + 0.5) * width - 0.5)
        iy = int((lat/math.pi + 0.5) * height  - 0.5)

        #not sure of this part to remap the image
        newpixel = pixel[ix,iy]
        img2.putpixel([(x+width/4) % width,y],newpixel)
        #I tries as mentionned in the following code to invert x and y in the two previous lines but the index error out of range comes back 
img2.show()
最佳答案
您的转型有两个步骤.第一步是投影球的变换,第二步是90°滚动.

90°的等角矩形图像只是图像宽度的四分之一的水平偏移.第一个转换更复杂:你基本上想要旋转球体,使得北极位于纬度0和经度0(几内亚湾的某个地方,如果你把thze地球作为参考.)

您可以通过这些步骤进行此转换;

>将每个像素的x和y位置转换为经度,-π≤long≤π,以及纬度,-π/2≤lat≤π/ 2.这是线性变换.
>在单位球面上创建相应经度和纬度的x,y和z坐标;正z是北极.
>旋转这些笛卡尔坐标.在您的情况下,您只需要交换一些维度,但这可能是任何转换矩阵的一般转换.
>计算旋转坐标的longituide和纬度.
>将新的经度和纬度转换为像素位置.

这是有效的C代码. (我知道你已经用Python标记了这个问题,但是下面的代码主要是在python中使用类似的公式.你必须小心:除了像素indixes x,y,ix和iy之外,所有数字都是浮点数.我本可以在Python中完成这项工作,但我没有Python图像库的经验.)

for (y = 0; y < height; y++) {
    for (x = 0; x < width; x++) {
        double xx = 2 * (x + 0.5) / width - 1.0;
        double yy = 2 * (y + 0.5) / height - 1.0;
        double lng = pi * xx;
        double lat = 0.5 * pi * yy;

        double X,Y,Z;
        double D;
        int ix,iy;

        Z = cos(lat) * cos(lng);    // corresponds to original x
        Y = cos(lat) * sin(lng);    // corresponds to original y
        X = -sin(lat);              // corresponds to original z

        D = sqrt(X*X + Y*Y);        // distance in the XY plane
        lat = atan2(Z,D);
        lng = atan2(Y,X);

        ix = (0.5 * lng / pi + 0.5) * width - 0.5;
        iy = (lat / pi + 0.5) * height - 0.5;

        dest[y][(x + width / 4) % width] = src[iy][ix];
                                    // width/4 offset ist the 90° roll
                                    // % width wraps the longitude
    }
}

结果图像的质量是可以的,但不如参考图像的质量好,特别是在极点附近.更好的算法可以平均并平滑颜色值.上面的算法仅将一个目标像素映射到源像素.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读