int StaticVertexBufferInterface::storeVertexAttributes(const gl::VertexAttribute &attrib, GLint start, GLsizei count, GLsizei instances)
{
    int attributeOffset = attrib.mOffset % attrib.stride();
    VertexElement element = { attrib.mType, attrib.mSize, attrib.stride(), attrib.mNormalized, attributeOffset, getWritePosition() };
    mCache.push_back(element);

    return VertexBufferInterface::storeVertexAttributes(attrib, start, count, instances);
}
static int ElementsInBuffer(const gl::VertexAttribute &attribute, unsigned int size)
{
    // Size cannot be larger than a GLsizei
    if (size > static_cast<unsigned int>(std::numeric_limits<int>::max()))
    {
        size = static_cast<unsigned int>(std::numeric_limits<int>::max());
    }

    GLsizei stride = attribute.stride();
    return (size - attribute.mOffset % stride + (stride - attribute.typeSize())) / stride;
}
示例#3
0
bool VertexBufferInterface::directStoragePossible(const gl::VertexAttribute &attrib,
                                                  const gl::VertexAttribCurrentValueData &currentValue) const
{
    gl::Buffer *buffer = attrib.mBoundBuffer.get();
    BufferStorage *storage = buffer ? buffer->getStorage() : NULL;

    if (!storage || !storage->supportsDirectBinding())
    {
        return false;
    }

    // Alignment restrictions: In D3D, vertex data must be aligned to
    //  the format stride, or to a 4-byte boundary, whichever is smaller.
    //  (Undocumented, and experimentally confirmed)
    size_t alignment = 4;
    bool requiresConversion = false;

    if (attrib.mType != GL_FLOAT)
    {
        gl::VertexFormat vertexFormat(attrib, currentValue.Type);

        unsigned int outputElementSize;
        getVertexBuffer()->getSpaceRequired(attrib, 1, 0, &outputElementSize);
        alignment = std::min<size_t>(outputElementSize, 4);

        requiresConversion = (mRenderer->getVertexConversionType(vertexFormat) & VERTEX_CONVERT_CPU) != 0;
    }

    bool isAligned = (static_cast<size_t>(attrib.stride()) % alignment == 0) &&
                     (static_cast<size_t>(attrib.mOffset) % alignment == 0);

    return !requiresConversion && isAligned;
}
static bool directStoragePossible(VertexBufferInterface* vb, const gl::VertexAttribute& attrib)
{
    gl::Buffer *buffer = attrib.mBoundBuffer.get();
    BufferStorage *storage = buffer ? buffer->getStorage() : NULL;

    const bool isAligned = (attrib.stride() % 4 == 0) && (attrib.mOffset % 4 == 0);

    return storage && storage->supportsDirectBinding() && !vb->getVertexBuffer()->requiresConversion(attrib) && isAligned;
}
int StaticVertexBufferInterface::lookupAttribute(const gl::VertexAttribute &attribute)
{
    for (unsigned int element = 0; element < mCache.size(); element++)
    {
        if (mCache[element].type == attribute.mType &&
            mCache[element].size == attribute.mSize &&
            mCache[element].stride == attribute.stride() &&
            mCache[element].normalized == attribute.mNormalized)
        {
            if (mCache[element].attributeOffset == attribute.mOffset % attribute.stride())
            {
                return mCache[element].streamOffset;
            }
        }
    }

    return -1;
}
示例#6
0
bool StaticVertexBufferInterface::storeVertexAttributes(const gl::VertexAttribute &attrib, const gl::VertexAttribCurrentValueData &currentValue,
                                                       GLint start, GLsizei count, GLsizei instances, unsigned int *outStreamOffset)
{
    unsigned int streamOffset;
    if (VertexBufferInterface::storeVertexAttributes(attrib, currentValue, start, count, instances, &streamOffset))
    {
        int attributeOffset = attrib.mOffset % attrib.stride();
        VertexElement element = { attrib.mType, attrib.mSize, attrib.stride(), attrib.mNormalized, attrib.mPureInteger, attributeOffset, streamOffset };
        mCache.push_back(element);

        if (outStreamOffset)
        {
            *outStreamOffset = streamOffset;
        }

        return true;
    }
    else
    {
        return false;
    }
}
示例#7
0
bool VertexBuffer11::storeVertexAttributes(const gl::VertexAttribute &attrib, GLint start, GLsizei count,
                                           GLsizei instances, unsigned int offset)
{
    if (mBuffer)
    {
        gl::Buffer *buffer = attrib.mBoundBuffer.get();

        int inputStride = attrib.stride();
        const VertexConverter &converter = getVertexConversion(attrib);

        ID3D11DeviceContext *dxContext = mRenderer->getDeviceContext();

        D3D11_MAPPED_SUBRESOURCE mappedResource;
        HRESULT result = dxContext->Map(mBuffer, 0, D3D11_MAP_WRITE_NO_OVERWRITE, 0, &mappedResource);
        if (FAILED(result))
        {
            ERR("Vertex buffer map failed with error 0x%08x", result);
            return false;
        }

        char* output = reinterpret_cast<char*>(mappedResource.pData) + offset;

        const char *input = NULL;
        if (buffer)
        {
            BufferStorage *storage = buffer->getStorage();
            input = static_cast<const char*>(storage->getData()) + static_cast<int>(attrib.mOffset);
        }
        else
        {
            input = static_cast<const char*>(attrib.mPointer);
        }

        if (instances == 0 || attrib.mDivisor == 0)
        {
            input += inputStride * start;
        }

        converter.conversionFunc(input, inputStride, count, output);

        dxContext->Unmap(mBuffer, 0);

        return true;
    }
    else
    {
        ERR("Vertex buffer not initialized.");
        return false;
    }
}
示例#8
0
bool StaticVertexBufferInterface::lookupAttribute(const gl::VertexAttribute &attribute, unsigned int *outStreamOffset)
{
    for (unsigned int element = 0; element < mCache.size(); element++)
    {
        if (mCache[element].type == attribute.mType &&
            mCache[element].size == attribute.mSize &&
            mCache[element].stride == attribute.stride() &&
            mCache[element].normalized == attribute.mNormalized &&
            mCache[element].pureInteger == attribute.mPureInteger)
        {
            if (mCache[element].attributeOffset == attribute.mOffset % attribute.stride())
            {
                if (outStreamOffset)
                {
                    *outStreamOffset = mCache[element].streamOffset;
                }
                return true;
            }
        }
    }

    return false;
}
static int elementsInBuffer(const gl::VertexAttribute &attribute, int size)
{
    int stride = attribute.stride();
    return (size - attribute.mOffset % stride + (stride - attribute.typeSize())) / stride;
}