Отображение сгенерированных кодом текстур в OpenGL - PullRequest
4 голосов
/ 12 апреля 2020

Я хочу предоставить Canvas API на основе OpenGL в Rust, поэтому я решил использовать один прямоугольник в OpenGL и обновить его текстуру. Я создал текстуру красной линии, и она не отображается так, как я ожидал.

Как создать текстуру:

let mut texture = 0;
gl::GenTextures(1, &mut texture);
gl::BindTexture(gl::TEXTURE_2D, texture); // all upcoming GL_TEXTURE_2D operations now have effect on this texture object
                                          // set the texture wrapping parameters
gl::TexParameteri(gl::TEXTURE_2D, gl::TEXTURE_WRAP_S, gl::REPEAT as i32); // set texture wrapping to gl::REPEAT (default wrapping method)
gl::TexParameteri(gl::TEXTURE_2D, gl::TEXTURE_WRAP_T, gl::REPEAT as i32);
// set texture filtering parameters
gl::TexParameteri(gl::TEXTURE_2D, gl::TEXTURE_MIN_FILTER, gl::NEAREST as i32);
gl::TexParameteri(gl::TEXTURE_2D, gl::TEXTURE_MAG_FILTER, gl::NEAREST as i32);
// load image, create texture and generate mipmaps

let mut data_ = [(0, 0, 0); 512 * 512];
gl::TexImage2D(
    gl::TEXTURE_2D,
    0,
    gl::RGB as i32,
    512,
    512,
    0,
    gl::RGB,
    gl::UNSIGNED_BYTE,
    &data_[0] as *const _ as *const c_void,
);

for i in 0..512 {
    data_[i + 512 * i] = (255, 0, 0);
}
gl::TexSubImage2D(
    gl::TEXTURE_2D,
    0,
    0,
    0,
    512,
    512,
    gl::RGB,
    gl::UNSIGNED_BYTE,
    &data_[0] as *const _ as *const c_void,
);

Как отобразить ее:

// bind Texture
gl::BindTexture(gl::TEXTURE_2D, texture);

// render container
ourShader.useProgram();
gl::BindVertexArray(VAO);
gl::DrawElements(gl::TRIANGLES, 6, gl::UNSIGNED_INT, ptr::null());

Вершинный шейдер:

#version 330 core
layout (location = 0) in vec3 aPos;
layout (location = 1) in vec3 aColor;
layout (location = 2) in vec2 aTexCoord;

out vec3 ourColor;
out vec2 TexCoord;

void main()
{
    gl_Position = vec4(aPos, 1.0);
    ourColor = aColor;
    TexCoord = vec2(aTexCoord.x, aTexCoord.y);
}

Фрагментный шейдер:

#version 330 core
out vec4 FragColor;

in vec3 ourColor;
in vec2 TexCoord;

uniform sampler2D texture1;

void main()
{
    FragColor = texture(texture1, TexCoord);
}

И я получаю:

Given image.

Я ожидал, что пиксели коснутся друг друга. Размер окна: 512х512, размер текстуры: 512х512. Кроме того, я попробовал линейную фильтрацию текс, но все тот же.

1 Ответ

1 голос
/ 12 апреля 2020

Ваш код не указывает тип массива data_. Похоже, что Rust выводит его тип как 32-разрядное целое число, тогда как вы сказали OpenGL, что ваши данные содержат байтов без знака . Это несоответствие заставляет ваши красные пиксели появляться только в каждой четвертой строке. Извините, я не знаю Rust, поэтому не могу сказать, как указать тип массива.

...