2017-02-11 3 views
2

, пожалуйста, рассмотрите следующую проблему.
У вас есть простая коробка и изображение, показанное внутри.
У вас также есть две текстуры, один красной и зеленый один ...
Вы инициализировать использованный texure из зеленой текстуры ...
Вашего окна отображает без изменений используемой текстуры на первом:
Как сохранить текстуру в фрагменте шейдера

enter image description here

Затененный круг вокруг вашей мыши, чтобы отобразить часть текстуры.
При нажатии кнопки мыши, заштрихованные области изменяются в красной текстуры,
, как показано ниже:
enter image description here

До сих пор так хорошо. Тем не менее, я искал довольно много, но я не могу
найти способ сохранения результата из фрагментарного шейдера до отображения
, используемой текстуры. Общая операция суммировалась бы до формы
смесь первой и второй текстур.

Вот мой отношение пиксельный шейдер:

#version 120 
uniform sampler2D red_texture, used_texture; 
uniform bool isMouseClicked; 
uniform float mousex, mousey; 
uniform float radius; //the radius of the painting circle 

void shadePixel(){ ... } 

void main(){ 
    //calculate the distance from mouse origin 
    float distance = sqrt(pow((gl_FragCoord.x - mousex), 2) + pow((gl_FragCoord.y - mousey), 2)); 

    if(distance<=radius && isMouseClicked){ 
    //used_texture <- red_tuxture 
    } 

    if(distance<=radius) shadePixel(); //make circle bound visible 
    else gl_FragColor = texture2D(used_texture, gl_TexCoord[0].xy); 
} 


Я хотел бы, чтобы позже получить текстуру таранить и сохранить на диск в виде изображения.
Итак, есть ли способ манипулировать текстурой через шейдер фрагмента?
Спасибо заранее.

ответ

1

Вы можете сделать «визуализацию текстуры».

  1. сделать изображение в текстуру
  2. спасти эту текстуру на диск
  3. отображения в окне.

Это пример того, как подготовить текстуру быть оказаны:

// create a texture "_textureId" 
glGenTextures(1, &_textureId); 
glBindTexture(TEXTURE_TARGET, _textureId); 
glTexParameteri(TEXTURE_TARGET, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 
glTexParameteri(TEXTURE_TARGET, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 
glTexParameteri(TEXTURE_TARGET, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); 
glTexParameteri(TEXTURE_TARGET, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); 
glTexImage2D(TEXTURE_TARGET, 0, YOUR_INTERNAL_FORMAT, width, height, 0, YOUR_FORMAT, GL_UNSIGNED_BYTE, 0); 

// create the framebuffer "_frameBuffer" and associate to the texture above 
glGenFramebuffers(1, &_frameBuffer); 
glBindFramebuffer(GL_FRAMEBUFFER, _frameBuffer); 
glBindTexture(TEXTURE_TARGET, _textureId); 
glFramebufferTexture(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, _textureId, 0); 
GLenum drawBuffers[1] = { GL_COLOR_ATTACHMENT0 }; 
glDrawBuffers(1, drawBuffers); 
if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) { 
    // error... 
} 

Код выше в основном создал пару текстур + фреймбуфером, так что вы можете оказать текстуру, если вы оказать связанный с фреймбуфером. Для того, чтобы сделать это вы можете сделать что-то вроде этого:

// do your normal render here... is goes to the image 
glBindFramebuffer(GL_FRAMEBUFFER, _frameBuffer); 

// render whatever you want... glViewPort, glClear, glDrawArrays, etc... 
// ... 

// Switch back to the "default framebuffer" 0... it means, your window. 
glBindFramebuffer(GL_FRAMEBUFFER, 0); 

На этом этапе вы можете снова визуализировать текстуру _textureId к окну, как вы хотите ... и, возможно, загрузить данные текстуры на GPU. .. это может быть сделано с чем-то вроде этого:

glBindTexture(TEXTURE_TARGET, _textureId); 
glGetTexImage(TEXTURE_TARGET, 0, YOUR_FORMAT, GL_UNSIGNED_BYTE, _data); 

Где _data представляет собой буфер с размером достаточно для вас, чтобы сохранить ваш растровое изображение.

+0

Спасибо, но я надеялся сделать это через шейдер. Вы знаете, что это возможно? –

+0

@FrustratedSoul: вы можете сделать это с помощью вычислительного шейдера и «imageStore» на новом оборудовании.Но я не вижу причин не использовать аппаратное обеспечение, которое можно смешать с помощью рендеринга-текстуры, как описано Вагнером. – ybungalobill

+0

", но я надеялся сделать это через шейдер:« Ну, вы вычисляете свой образ (или все, что хотите вычислить), используя шейдер фрагмента и выводя его в текстуру, я действительно не понимаю, почему вы не в порядке с этим решением – Zouch

Смежные вопросы