Матрица вершинных шейдеров нарушена?
OpenGL ES 2.0 на Android: очень простой шейдер, который работает практически на всех устройствах, но не на Huawei Ascend P6:
вершинный шейдер:
attribute vec2 a_position;
attribute vec2 a_texcoords;
uniform mat4 u_matrix;
varying mediump vec2 v_texcoords;
void main()
{
gl_Position = u_matrix * vec4(a_position, 0.0, 1.0);
v_texcoords = a_texcoords;
}
фрагментный шейдер:
uniform lowp sampler2D u_textureUnit;
varying mediump vec2 v_texcoords;
void main()
{
gl_FragColor = texture2D(u_textureUnit, v_texcoords);
}
Программа шейдера используется для рисования квадратов в плоскости z=0 (в виде 4-х вершинных треугольных полос), и a_position задается в мировом пространстве. a_texcoords - стандартные (0,0)->(1,1) координаты. u_matrix устанавливается с перспективной камеры, т.е. проекционной матрицы *viewmatrix. когда я изменяю расстояние в матрице вида (увеличение), в один момент плитки исчезают, и отображается только чистый цвет, как будто фрагментный шейдер никогда не выполнялся. когда я снова уменьшаю масштаб, я снова вижу плитки.
Теперь начинается странная вещь: когда я (в коде C++) преобразую позицию, чтобы обрезать пространство и передать ее шейдеру как attribute vec4
и напишите это без изменений gl_Position
на устройстве Huawei все работает как положено. Я также сравнил результаты u_matrix * vec4(a_position, 0.0, 1.0)
с позицией пространства клипа, которую я прошел, и оказывается, что они почти равны координатам пространства клипа, которые я передаю со стороны процессора. (на самом деле, я сделал перспективное разделение на обоих, а затем испустил vec4(1)-vec4(abs(difference).xyz*20.0,0.0)
как цвет - он едва отличим от белого, поэтому разница очень мала, я думаю, просто другая арифметика с плавающей запятой.)
Есть идеи, что происходит? Тесты ножниц, глубины и трафарета отключены, ближняя и дальняя плоскости камеры в порядке, отбраковка задней поверхности отключена. Не стесняйтесь спрашивать более подробно...
update1: если я наклоню камеру, чтобы она не выглядела точно в -Z, я получу тот же артефакт, но теперь он выглядит как отсечение почти в плоскости (я могу увеличить до состояния, когда только половина экрана пуста). Но я понятия не имею, как это может произойти; мой ближний самолет установлен на 20 (метров); но артефакт возникает на расстоянии камеры <-> z=0 от ~1300 (метров).