Beispiel #1
0
func newOctree(file string) (uint32, []uint32, error) {
	var (
		header  pack.OctreeHeader
		texture uint32
		data    []uint32
	)

	fp, err := os.Open(file)
	if err != nil {
		return 0, nil, err
	}
	defer fp.Close()

	if err := pack.DecodeHeader(fp, &header); err != nil {
		return 0, nil, err
	}

	if header.Format != pack.MipR8G8B8A8UnpackUI32 {
		return 0, nil, errors.New("invalid octree format")
	}
	nodeSize := uint64(1 + 8)

	var maxSize int32
	gl.GetIntegerv(gl.MAX_TEXTURE_SIZE, &maxSize)

	numInts := header.NumNodes * nodeSize
	if maxSize*maxSize < int32(numInts) {
		panic("octree does not fit on GPU")
	}

	var (
		height int32
		width  = maxSize
	)

	for height < width {
		maxSize = width
		height = int32(numInts/uint64(width)) + 1
		width /= 2
	}

	fmt.Printf("Octree is loaded in an %vx%v, R32UI, 2D texture.\n", maxSize, height)

	textureSize := maxSize * height
	data = make([]uint32, textureSize)

	for i := uint64(0); i < header.NumNodes; i++ {
		start := i * nodeSize
		if err := binary.Read(fp, binary.BigEndian, data[start:start+nodeSize]); err != nil {
			return 0, nil, err
		}

		// Recalculate alpha value.
		data[start] &= 0xffffff00
		for j := uint64(1); j < 9; j++ {
			if data[start+j] > 0 {
				data[start] |= uint32(0x100) >> j
			}
		}
	}

	gl.GenTextures(1, &texture)
	gl.ActiveTexture(gl.TEXTURE0)
	gl.BindTexture(gl.TEXTURE_2D, texture)

	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,
		gl.R32UI,
		maxSize,
		height,
		0,
		gl.RED_INTEGER,
		gl.UNSIGNED_INT,
		gl.Ptr(data))

	if glErr := gl.GetError(); glErr != gl.NO_ERROR {
		err = fmt.Errorf("GL error, loading octree: %x", glErr)
	}

	return texture, data, err
}
Beispiel #2
0
// ActiveTexture implements the opengl.OpenGl interface.
func (native *OpenGl) ActiveTexture(texture uint32) {
	gl.ActiveTexture(texture)
}