使用EncodeToJPG将Texture2D转换为Byte [](在OpenVR中)

时间:2018-07-25 09:02:18

标签: c# unity3d texture2d opencvsharp openvr

我有一个问题!

我只想要...使用 EncodeToJPG()函数将 Texture2D 转换为 Byte []

我的工作空间是Unity和C#脚本+ OpenCvSharp。

也许您认为这很容易,但是存在一些问题。

此脚本使用OpenVR(HTC VIVE)。

无论如何,这是我的消息来源。

var source = SteamVR_TrackedCamera.Source(undistorted);

//Receive texture data from VR.
texture = source.texture;

//Debug.Log(source.texture.width + "/" + source.texture.height);    
//size : 612 /460
if (texture == null)
{
    return;
}

//Input texture data into material, and it's in unity (quad GameObject).
//this G.O print display like camera
material.mainTexture = texture;


//here is my src, I want to save Image but texture.EncodeToJPG has some error.
Cv2.ImShow("_Texture ...", Mat.FromImageData(texture.EncodeToJPG()));
Cv2.ImWrite(SavePath+ "Image.jpg", Mat.FromImageData(texture.EncodeToJPG()));

还有...有问题。变量纹理是异常的Texture2D类型。

if (_texture == null)
{
    _texture = Texture2D.CreateExternalTexture((int)header.nWidth, (int)header.nHeight, TextureFormat.RGBA32, false, false, nativeTex);
    //_texture = new Texture2D(612, 460, TextureFormat.RGBA32, false);

    uint width = 0, height = 0;
    var frameBounds = new VRTextureBounds_t();
    if (trackedCamera.GetVideoStreamTextureSize(deviceIndex, frameType, ref frameBounds, ref width, ref height) == EVRTrackedCameraError.None)
    {
        // Account for textures being upside-down in Unity.
        frameBounds.vMin = 1.0f - frameBounds.vMin;
        frameBounds.vMax = 1.0f - frameBounds.vMax;
        this.frameBounds = frameBounds;
    }
}
else
{
    _texture.UpdateExternalTexture(nativeTex);
    //_texture.Apply();
}

_texture 是由函数 CreateExternalTexture 创建的,它具有名为 nativeTex 的Intptr类型的参数。

我不知道该怎么办?

+++编辑!错误显示+++

enter image description here

2 个答案:

答案 0 :(得分:0)

由于Unity可能无法直接访问外部纹理,所以建议您先执行Graphics.Blit()将其纹理通过GPU传输到RenderTexture。

一旦您的RenderTexture中包含纹理,您就需要跳过一个箍,然后将RenderTexture.active中的readpixels转移到另一个基于RAM的标准Texture2D中,然后就可以对其进行编码了。

记住在执行ReadPixels()之后要应用Apply()纹理

答案 1 :(得分:0)

声明了此功能:

public static readonly BindableProperty ParamProperty =
            BindableProperty.Create(
                nameof(Param),
                typeof(string),
                typeof(GridTemplate),
                default(string));

public string Param
{
   get { return (string)GetValue(ParamProperty); }
   set { SetValue(ParamProperty, value); }
}

并在void Update()中使用ReadExternalTexture函数:

private Texture2D ReadExternalTexture(Texture externalTexture)
{
    Texture2D myTexture2D = new Texture2D(texture.width, texture.height);
    //myTexture2D => empty Texture2D type variable
    if (myTexture2D == null)
    {
        Debug.Log("var: myTexture2D is null state.");
        myTexture2D = new Texture2D(texture.width, texture.height);
    }

    //Make RenderTexture type variable
    RenderTexture tmp = RenderTexture.GetTemporary(
    externalTexture.width,
    externalTexture.height,
    0,
    RenderTextureFormat.ARGB32,
    RenderTextureReadWrite.sRGB);

    Graphics.Blit(externalTexture, tmp);
    RenderTexture previous = RenderTexture.active;
    RenderTexture.active = tmp;

    myTexture2D.ReadPixels(new UnityEngine.Rect(0, 0, tmp.width, tmp.height), 0,     0);
    myTexture2D.Apply();

    RenderTexture.active = previous;
    RenderTexture.ReleaseTemporary(tmp);

    return myTexture2D;
}

这完全有效!