C++ 如何在现代OpenGL中动态绑定多个纹理坐标集的数组以进行混合?

C++ 如何在现代OpenGL中动态绑定多个纹理坐标集的数组以进行混合?,c++,opengl,C++,Opengl,我试图了解绑定包含不同UV坐标值的多个纹理的整个系统,特别是对于贴图平铺(重复),以便混合包含不同标量值的反照率+法线贴图。动态地将多个纹理坐标设置为一个网格在许多情况下都是有益的——其中之一是法线贴图细节在皮肤、生锈的金属等方面会非常突出。只需将UV坐标值缩放到相对较高的值,并将反照率贴图比例设置为1,即可完成此操作 如何将这些纹理COORD集合从C++传递到GLSL着色器,以及什么是最有效的动态流水线来进行实时渲染?< /P> 我已经尝试过通过许多位置布局将多个数组解析为GLSL,但是这对于

我试图了解绑定包含不同UV坐标值的多个纹理的整个系统,特别是对于贴图平铺(重复),以便混合包含不同标量值的反照率+法线贴图。动态地将多个纹理坐标设置为一个网格在许多情况下都是有益的——其中之一是法线贴图细节在皮肤、生锈的金属等方面会非常突出。只需将UV坐标值缩放到相对较高的值,并将反照率贴图比例设置为1,即可完成此操作

如何将这些纹理COORD集合从C++传递到GLSL着色器,以及什么是最有效的动态流水线来进行实时渲染?< /P> 我已经尝试过通过许多位置布局将多个数组解析为GLSL,但是这对于动态情况来说过于静态

这是我的顶点结构,但我只分析一组顶点位置和一组纹理坐标:

    struct VertexElement {
     uint16_t               componentSize;
     std::vector<float>     data;

     VertexElement(uint16_t comp_size, std::vector<float> vertex_data)
     {
    componentSize = comp_size;
    data = vertex_data;
     }
    };

    struct Vertex {
     uint16_t stride;
     std::vector<VertexElement> vertexElements;

     inline Vertex() = default;
     inline Vertex(uint16_t _stride, std::vector<VertexElement> 
         _vertex_elements) 
         {
    stride = _stride;
    vertexElements = _vertex_elements;
     }
    };
结构顶点元素{
uint16_t元件尺寸;
std::矢量数据;
顶点元素(uint16组件大小,标准::向量顶点数据)
{
组件大小=组件大小;
数据=顶点数据;
}
};
结构顶点{
uint16步;
std::向量顶点元素;
内联顶点()=默认值;
内联顶点(uint16,标准::向量
_顶点(U元素)
{
步幅=_步幅;
顶点元素=_顶点元素;
}
};
本质上,我希望组合包含完全不同坐标值的多个纹理,而不必像这样在GLSL中静态分配:

       location (layout = 0) in vec2 texCord0
       location (layout = 1) in vec2 texCord1        <----- BAD!!
       location (layout = 2) in vec2 texCord3
       ...
vec2 texCord0中的位置(布局=0)
位置(layout=1)在vec2 texCord1中,着色器之间的接口始终是静态定义的。着色器始终具有X个输入

如果您希望动态确定某些信息,那么您必须使用现有工具(映像加载/存储、SSBO、UBOs等)自己读取这些信息。这对于顶点着色器是完全可能的,因为
gl\u VertexID
索引可以用作数组的索引

但是,一般来说,人们不需要这样做。他们只是定义一个特定的顶点格式,并坚持使用它。事实上,您的特定用例似乎不需要这样做,因为您只是更改纹理坐标的值,而不是是否正在使用它们

我需要动态调整texcoord集的大小,以便进行实时编辑

这实际上是不可能的,特别是对于您概述的用例

考虑一个法线贴图。使用法线贴图和不使用法线贴图之间的差别很大。不仅仅是传递给VS的参数,还有着色器的基本性质

法线贴图通常是切线空间。所以你的着色器现在需要一个完整的NBT矩阵。你可能需要把这个矩阵传递给你的片段着色器,片段着色器会用它从法线贴图构造法线。当然,如果不使用法线贴图,只需获得逐顶点法线。因此,您谈论的是对代码结构的实质性更改,而不仅仅是输入


着色器只是字符串,因此您可以随意动态构建它们。但是,这将比VS获得的输入复杂得多。

因此,您希望每个顶点具有多个纹理坐标,但不希望在着色器布局中硬编码这些纹理坐标?在布局中使用一组大小为整数的texcoords怎么样?“其中之一是,普通地图细节在皮肤、生锈的金属等方面会非常突出。只需将UV Coords值缩放到相对较高的值,并将反照率地图比例设置为1即可完成。”这没有意义。纹理坐标的值不会影响从纹理获得的值,除非它从不同的位置选择值。也就是说,较大的UV值并不意味着从纹理获取的值将“突出”。任何缩放都应该应用于从纹理中获取的值。对于这种微妙的解释,我深表歉意-例如,如果您查看Substance Painter,可以唯一地调整单个纹理的UV比例,以便借助曲率和空腔贴图创建更好的真实感。我想知道是否可以使用OpenGL和GLSL来实现这一点。感谢您说明实现这一点的可能性。我本来希望制作一个texcoord管道系统,类似于Unreal的材质编辑器,用户可以使用UV对象节点调整任何纹理UV标量,实时单独编辑ST值。也许只有在Direct3D中才有可能,因为“不真实”倾向于在大多数情况下使用此API。我想我只需要通过在Photoshop中优化平铺纹理,或者创建一个ID映射系统来创建一个解决方案。