Esempio n. 1
0
void gpuDrawVbo(u32 vbo) {
    VboData* vboData = (VboData*) vbo;
    if(vboData == NULL || vboData->data == NULL) {
        return;
    }

    gpuUpdateState();

    static u32 attributeBufferOffset = 0;
    GPU_SetAttributeBuffers(vboData->attributeCount, (u32*) osConvertVirtToPhys((u32) vboData->data), vboData->attributes, vboData->attributeMask, vboData->attributePermutations, 1, &attributeBufferOffset, &vboData->attributePermutations, &vboData->attributeCount);
    if(vboData->indices != NULL) {
        GPU_DrawElements((GPU_Primitive_t) vboData->primitive, (u32*) vboData->indices, vboData->numVertices);
    } else {
        GPU_DrawArray((GPU_Primitive_t) vboData->primitive, vboData->numVertices);
    }
}
Esempio n. 2
0
void RectangleShape::draw()
{
	if (!_device->isInitialized() || !_visible)
		return;

	updateTransform();
	
	if (_color.a > 0)
	{
		ShaderProgram::setUniform(UNIFORM_MODELVIEW_NAME, getCombinedTransform());

#ifdef _3DS

		auto vertices = VertexPool::getInstance()->
			pushVertices<VertexPositionTexture>(4);

		vertices[0].position = Vec2(0, 0);
		vertices[1].position = Vec2(_size.x, 0);
		vertices[2].position = Vec2(0, _size.y);
		vertices[3].position = Vec2(_size.x, _size.y);

		vertices[0].texcoord = Vec2::Zero;
		vertices[1].texcoord = Vec2::Zero;
		vertices[2].texcoord = Vec2::Zero;
		vertices[3].texcoord = Vec2::Zero;

		//=========================================================================

		GPU_SetTexEnv(0,
			GPU_TEVSOURCES(GPU_CONSTANT, GPU_CONSTANT, GPU_CONSTANT),
			GPU_TEVSOURCES(GPU_CONSTANT, GPU_CONSTANT, GPU_CONSTANT),
			GPU_TEVOPERANDS(0, 0, 0),
			GPU_TEVOPERANDS(0, 0, 0),
			GPU_REPLACE, GPU_REPLACE,
			_color.r | _color.g << 8 | _color.b << 16 | _color.a << 24);

		u32 bufferOffsets[] = { 0x00 };
		u64 bufferPermutations[] = { 0x10 };
		u8 bufferNumAttributes[] = { 2 };

		GPU_SetAttributeBuffers(
			2,
			(u32*)osConvertVirtToPhys((u32)vertices),
			GPU_ATTRIBFMT(0, 2, GPU_FLOAT) |
			GPU_ATTRIBFMT(1, 2, GPU_FLOAT),
			0xFFFC,
			0x10,
			1,
			bufferOffsets,
			bufferPermutations,
			bufferNumAttributes);

		GPU_DrawArray(GPU_TRIANGLE_STRIP, 0, 4);

#else
		Vec4 c = _color.toVector();

		float vertices[] =
		{
			0, 0, -0.5f, c.x, c.y, c.z, c.w, 0, 0,
			_size.x, 0, -0.5f, c.x, c.y, c.z, c.w, 0, 0,
			0, _size.y, -0.5f, c.x, c.y, c.z, c.w, 0, 0,
			_size.x, _size.y, -0.5f, c.x, c.y, c.z, c.w, 0, 0
		};

		glUniform1i(ShaderProgram::getCurrentProgram()->
			getUniformLocation("textureEnabled"), false);

		glBindBuffer(GL_ARRAY_BUFFER, _vbo);
		glBufferSubData(GL_ARRAY_BUFFER, 0, sizeof(float) * 36, vertices);
		glBindBuffer(GL_ARRAY_BUFFER, 0);

		glBindVertexArray(_vao);
		glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
		glBindVertexArray(0);
#endif // _3DS
	}

	if (getOutlineColor().a > 0)
	{
		_outline.setTransform(getCombinedTransform());

		_outline.setLine(0, 0, _size.x, 0);
		_outline.draw();
		_outline.setLine(_size.x, 0, _size.x, _size.y);
		_outline.draw();
		_outline.setLine(0, _size.y, _size.x, _size.y);
		_outline.draw();
		_outline.setLine(0, 0, 0, _size.y);
		_outline.draw();
	}

	Node::draw();
}
Esempio n. 3
0
void RenderTarget::draw(const Vertex* vertices, unsigned int vertexCount,
                        PrimitiveType type, const RenderStates& states)
{
    // Nothing to draw?
    if (!vertices || (vertexCount == 0))
        return;

    // Vertices allocated in the stack (common) can't be converted to physical address
#ifndef EMULATION
    if (osConvertVirtToPhys((u32)vertices) == 0)
    {
        err() << "RenderTarget::draw() called with vertex array in inaccessible memory space." << std::endl;
        return;
    }
#endif

    // GL_QUADS is unavailable on OpenGL ES
    if (type == Quads)
    {
        err() << "cpp3ds::Quads primitive type is not supported on OpenGL ES platforms, drawing skipped" << std::endl;
        return;
    }
#define GL_QUADS 0

    if (activate(true))
    {
        // First set the persistent OpenGL states if it's the very first call
        if (!m_cache.glStatesSet)
            resetGLStates();

        // Check if the vertex count is low enough so that we can pre-transform them
        bool useVertexCache = (vertexCount <= StatesCache::VertexCacheSize);
        if (useVertexCache)
        {
            // Pre-transform the vertices and store them into the vertex cache
            for (unsigned int i = 0; i < vertexCount; ++i)
            {
                Vertex& vertex = m_cache.vertexCache[i];
                vertex.position = states.transform * vertices[i].position;
                vertex.color = vertices[i].color;
                vertex.texCoords = vertices[i].texCoords;
            }

            // Since vertices are transformed, we must use an identity transform to render them
            if (!m_cache.useVertexCache)
                applyTransform(Transform::Identity);
        }
        else
        {
            applyTransform(states.transform);
        }

        // Apply the view
        if (m_cache.viewChanged)
            applyCurrentView();

        // Apply the blend mode
        if (states.blendMode != m_cache.lastBlendMode)
            applyBlendMode(states.blendMode);

        // Apply the texture
        Uint64 textureId = states.texture ? states.texture->m_cacheId : 0;
        if (textureId != m_cache.lastTextureId)
            applyTexture(states.texture);

        // Apply the shader
        if (states.shader)
            applyShader(states.shader);

        // If we pre-transform the vertices, we must use our internal vertex cache
        if (useVertexCache)
        {
            // ... and if we already used it previously, we don't need to set the pointers again
            if (!m_cache.useVertexCache)
                vertices = m_cache.vertexCache;
            else
                vertices = NULL;
        }

        // Setup the pointers to the vertices' components
        if (vertices)
        {
#ifdef EMULATION
            const char* data = reinterpret_cast<const char*>(vertices);
            glCheck(glVertexPointer(2, GL_FLOAT, sizeof(Vertex), data + 0));
            glCheck(glColorPointer(4, GL_UNSIGNED_BYTE, sizeof(Vertex), data + 8)); // 8 = sizeof(Vector2f)
            glCheck(glTexCoordPointer(2, GL_FLOAT, sizeof(Vertex), data + 12)); // 12 = 8 + sizeof(Color)
#else
            // Temorary workaround until gl3ds can get VAO gl*Pointer functions working
            u32 bufferOffsets[] = {0};
            u64 bufferPermutations[] = {0x210};
            u8 bufferAttribCounts[] = {3};
            GPU_SetAttributeBuffers(
                3, // number of attributes
                (u32*)osConvertVirtToPhys((u32)vertices),
                GPU_ATTRIBFMT(0, 2, GPU_FLOAT) | GPU_ATTRIBFMT(1, 4, GPU_UNSIGNED_BYTE) | GPU_ATTRIBFMT(2, 2, GPU_FLOAT),
                0xFF8, //0b1100
                0x210,
                1, //number of buffers
                bufferOffsets,
                bufferPermutations,
                bufferAttribCounts // number of attributes for each buffer
            );
#endif
        }

        // Find the OpenGL primitive type
        static const GLenum modes[] = {GL_POINTS, GL_LINES, GL_LINE_STRIP, GL_TRIANGLES,
                                       GL_TRIANGLE_STRIP, GL_TRIANGLE_FAN, GL_QUADS
                                      };
        GLenum mode = modes[type];

        // Draw the primitives
        glCheck(glDrawArrays(mode, 0, vertexCount));

        // Unbind the shader, if any
        if (states.shader)
            applyShader(NULL);

        // Update the cache
        m_cache.useVertexCache = useVertexCache;
    }
}