ОБНОВЛЕНО. Я пытаюсь нарисовать текстуру с помощью openGL ES3 и использовать инстансное рисование для своего приложения для рисования. Это мой вершинный шейдер
#version 300 es
precision highp float;
uniform mat3 u_Matrix;
in vec2 Position;
in vec2 TexPosition;
struct Data {
vec2 pos;
vec2 scale;
uint color;
float rotation;
};
layout(std140) uniform InstanceData {
Data data[256];
};
out vec4 v_Color;
out vec2 v_TexPosition;
void main() {
vec2 endPos = Position * data[gl_InstanceID].scale;
if (data[gl_InstanceID].rotation != 0.0) {
float cos = cos(data[gl_InstanceID].rotation);
float sin = sin(data[gl_InstanceID].rotation);
endPos = vec2(endPos.x * cos - endPos.y * sin, endPos.x * sin +
endPos.y * cos) + data[gl_InstanceID].pos;
} else {
endPos = endPos + data[gl_InstanceID].pos;
}
uint fColor = data[gl_InstanceID].color;
v_Color.r = float((fColor & 0x00FF0000U) >> 16) / 255.0;
v_Color.g = float((fColor & 0x0000FF00U) >> 8) / 255.0;
v_Color.b = float(fColor & 0x000000FFU) / 255.0;
v_Color.a = float((fColor & 0xFF000000U) >> 24) / 255.0;
v_TexPosition = TexPosition;
gl_Position = vec4(u_Matrix * vec3(endPos, 1.0), 1.0);
}
а это мой fragment_shader
#version 300 es
precision highp float;
in vec2 v_TexPosition;
in vec4 v_Color;
uniform sampler2D u_Texture2D;
out vec4 fragColor;
void main() {
vec4 color = texture(u_Texture2D, v_TexPosition);
fragColor = vec4(v_Color.rgb, color.a * v_Color.a);
}
Когда я создал программу, прикрепил шейдеры и пытаюсь связать программу, приложение зависает на строке glLinkProgram. Шейдеры и программа имеют нормальный id.
Это нормально работает на некоторых устройствах (sony xperia Z-android 5.0, smasung s7 edge android 7, nexus 5x - android 7, nexus 6p - android 7), но это не работает на других устройствах (motX-android 5.1, smasung с5 андроид 6.0). Все устройства имеют версию Android выше 5.0, и в коде я проверил поддержку opengl ES3.
Есть ли для этого какая-то причина? Это с устройства (как это проверить)? или я что-то не так сделал? Я передал данные в instanceBuffer следующим образом:
instanceBuffer.putFloat(posX);
instanceBuffer.putFloat(posY);
instanceBuffer.putFloat(scaleX);
instanceBuffer.putFloat(scaleY);
instanceBuffer.putInt(colorARGB);
instanceBuffer.putFloat((float) Math.toRadians(rotate));
instanceBuffer.position(instanceBuffer.position() + 8);
используется +8 смещений, потому что элементы чтения данных структуры имеют размер vec4 (16 байт)
Когда я пишу свою структуру только с одним vec4 :
struct Data {
vec4 posAndScale;
};
и передать данные:
instanceBuffer.putFloat(posX);
instanceBuffer.putFloat(posY);
instanceBuffer.putFloat(scaleX);
instanceBuffer.putFloat(scaleY);
Это работает на всех устройствах, но когда я добавил еще один vec4 :
struct Data {
vec4 posAndScale;
vec4 color;
};
и передать данные
instanceBuffer.putFloat(posX);
instanceBuffer.putFloat(posY);
instanceBuffer.putFloat(scaleX);
instanceBuffer.putFloat(scaleY);
instanceBuffer.putFloat(color.r);
instanceBuffer.putFloat(color.g);
instanceBuffer.putFloat(color.b);
instanceBuffer.putFloat(color.a);
приложение не зависает, но ничего не происходит, когда я пытаюсь рисовать. Похоже, что на некоторых устройствах std140 работает по-другому или данные не передаются в шейдер при написании структуры с 2 vec4-s