Создание более одного фреймбуфера - PullRequest
0 голосов
/ 11 июня 2018

Мне удалось создать один кадровый буфер и отобразить его в виде текстуры.Однако когда я пытаюсь создать еще один, я начинаю получать очень странные результаты.

Я узнал, что сначала генерирование кадрового буфера, а затем его текстур должно дать мне правильные результаты.Однако в моем случае у меня есть текстура, которая «разделяется» между первым и вторым кадровым буфером.См. Код:

func (o *OpenGL) Init() {
    o.opaqueFBO = newFramebuffer()
    o.transparentFBO = newFramebuffer()

    // OPAQUE FBO
    gl.BindFramebuffer(gl.FRAMEBUFFER, o.opaqueFBO)
    opaqueFBOAttachments := []attachment{
        attachment{&o.opaqueTex0, gl.RGBA, gl.RGBA, gl.FLOAT, gl.COLOR_ATTACHMENT0},
        attachment{&o.sharedDepthBuffer, gl.DEPTH_COMPONENT, gl.DEPTH_COMPONENT, gl.FLOAT, gl.DEPTH_ATTACHMENT},
    }
    o.attachFramebufferTextures(o.opaqueFBO, opaqueFBOAttachments)
    gl.BindFramebuffer(gl.FRAMEBUFFER, 0)

    // TRANSPARENT FBO
    gl.BindFramebuffer(gl.FRAMEBUFFER, o.transparentFBO)
    transparentFBOAttachments := []attachment{
        attachment{&o.transparentTex0, gl.RGB, gl.RGB, gl.FLOAT, gl.COLOR_ATTACHMENT0},
        attachment{&o.transparentTex1, gl.RGBA, gl.RGBA, gl.FLOAT, gl.COLOR_ATTACHMENT1},
        attachment{&o.sharedDepthBuffer, gl.DEPTH_COMPONENT, gl.DEPTH_COMPONENT, gl.FLOAT, gl.DEPTH_ATTACHMENT},
    }
    o.attachFramebufferTextures(o.transparentFBO, transparentFBOAttachments)
    gl.BindFramebuffer(gl.FRAMEBUFFER, 0)
}

// attachFramebufferTextures attaches textures to an existing framebuffer. Has a check to reuse one if it already has a value
func (o *OpenGL) attachFramebufferTextures(fib uint32, a []attachment) {
    for _, att := range a {
        if *att.textureID <= 0 {
            gl.GenTextures(1, att.textureID)
            gl.BindTexture(gl.TEXTURE_2D, *att.textureID)
            gl.TexParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.REPEAT)
            gl.TexParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.REPEAT)
            gl.TexParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST)
            gl.TexParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST)
            gl.TexImage2D(gl.TEXTURE_2D, 0, att.internalFormat, int32(o.screenWidth), int32(o.screenHeight), 0, att.format, att.typ, nil)
        } else {
            log.Printf("> DEBUG: Texture %v seems to be shared with another framebuffers", *att.textureID)
            gl.BindTexture(gl.TEXTURE_2D, *att.textureID)
        }

        gl.FramebufferTexture2D(gl.FRAMEBUFFER, att.point, gl.TEXTURE_2D, *att.textureID, 0)
        // gl.BindTexture(gl.TEXTURE_2D, 0)
    }

    if gl.CheckFramebufferStatus(gl.FRAMEBUFFER) != gl.FRAMEBUFFER_COMPLETE {
        log.Fatalf("Framebuffer Error Hex: 0x%x\nNow go look it up here: https://raw.githubusercontent.com/go-gl/gl/master/v4.5-core/gl/package.go", gl.CheckFramebufferStatus(gl.FRAMEBUFFER))
    }
}

// newFramebuffer generates and returns a new framebuffer
func newFramebuffer() uint32 {
    var fid uint32
    gl.GenFramebuffers(1, &fid)
    return fid
}

type attachment struct {
    textureID      *uint32
    internalFormat int32
    format         uint32
    typ            uint32
    point          uint32
}

Итак, несколько моментов, которые я заметил при тестировании, таковы:

- Изменение порядка блоков кода "OPAQUE FBO" и "TRANSPARENT FBO"дать разные результаты.Зачем?Они оба связаны, когда я использую их, а затем не связаны, когда я закончу.

- Когда я рендеринг каждого кадрового буфера в одиночку, я ожидаю результатов.Однако когда я в конечном итоге отрисовываю их в стандартный кадровый буфер как текстуры, я просто получаю черный экран.Черный, я думаю, может иметь отношение к следующему коду

bindFramebuffer(o.transparentFBO)
gl.Clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT)
gl.DrawBuffers(2, &[]uint32{gl.COLOR_ATTACHMENT0, gl.COLOR_ATTACHMENT1}[0])
gl.ClearBufferfv(gl.COLOR, 0, &[]float32{0, 0, 0, 1}[0])
gl.ClearBufferfv(gl.COLOR, 1, &[]float32{1, 1, 1, 1}[0])

Обновление

Таким образом, черный экран должен был делать то, как я связываю текстуры с шейдерами.Сначала я должен был выполнить gl.ActiveTexture(gl.TEXTURE0 + n) ДО , запустить gl.BindTexture(...).Очень душно, но это то, что есть.

Единственная проблема, которую я до сих пор имею, заключается в том, чтобы как-то «разделить» этот буфер глубины между двумя FBO.Я даже не уверен больше, если это то, что я должен делать, но код, на который я ссылаюсь, кажется, предлагает это.

...