Пример #1
0
void
loadMeshes( const std::string&  fn,
            const CalCoreModel* calCoreModel,
            MeshesVector& meshes )
    throw (std::runtime_error)
{
    FILE* f = fopen( fn.c_str(), "rb" );

    if ( f == NULL )
    {
        throw std::runtime_error( "Can't open " + fn );
    }

    FileCloser closeOnExit( f );
//    FileBuffer setReadBufferOfSize( f, 1*1024*1024 ); <- not so much difference

    // -- Check version --
    int version;

    READ_I32( version );
    if ( version != HW_MODEL_FILE_VERSION )
    {
        fclose( f );
        throw std::runtime_error( "Incorrect file version " + fn + ". Try rerun osgCalPreparer." );
    }

    // -- Read mesh descriptions --
    int meshesCount = 0;

    READ_I32( meshesCount );
    meshes.resize( meshesCount );

    for ( int i = 0; i < meshesCount; i++ )
    {
        MeshData* m = new MeshData;
        meshes[i] = m;

        // -- Read name --
        int nameBufSize;
        READ_I32( nameBufSize );
        if ( nameBufSize > 1024 )
        {
            throw std::runtime_error( "Too long mesh name (incorrect meshes.cache file?)." );
        }
        char name[ 1024 ];
        READ_( m->name, name, nameBufSize );
        m->name = std::string( &name[0], &name[ nameBufSize ] );

        // -- Read material --
        int coreMaterialThreadId;
        READ_I32( coreMaterialThreadId );

        m->coreMaterial = const_cast< CalCoreModel* >( calCoreModel )->
            getCoreMaterial( coreMaterialThreadId );

        // -- Read bone parameters --
        READ_I32( m->rigid );
        READ_I32( m->rigidBoneId );
        READ_I32( m->maxBonesInfluence );

        // -- Read bonesIndices --
        int biSize = 0;
        READ_I32( biSize );
        m->bonesIndices.resize( biSize );
        for ( int bi = 0; bi < biSize; bi++ )
        {
            READ_I32( m->bonesIndices[ bi ] );
        }

        // -- Read boundingBox --
        assert( sizeof ( m->boundingBox ) == 6 * 4 ); // must be 6 floats
        READ_STRUCT( m->boundingBox );
    }

    // -- Read meshes buffers --
    while ( !feof( f ) )
    {
        readBuffer( meshes, f, fn );
    }
}
Пример #2
0
int read_thrift(char *ptr, int len, ThriftMessage *tm)
{
    int off;
    int x;
    int fieldId;
    char fieldType;

    memset(tm, 0, sizeof(*tm));

    off = 0;

    READ_I32(ptr, off, len, x);
    // ASSERT version stuff
    tm->messageType = x & 0xff;

    READ_STRING(ptr, off, len, tm->name_len, tm->name_ptr);
    
    READ_I32(ptr, off, len, tm->seqid);

    while(1) {
        READ_I8(ptr, off, len, fieldType);
        if(fieldType == T_STOP)
            break;

        READ_I16(ptr, off, len, fieldId);
        if(fieldId > MAX_FIELD_ID || fieldId < 0) {
            printf("Ignoring field with out of range id, id = %d, max = %d",
                  MAX_FIELD_ID, fieldId);
            fieldId = -1;
        }

        if(fieldId >= 0) {
            tm->fields[fieldId].present = 1;
            tm->fields[fieldId].fieldType = fieldType;
        }
        
        switch(fieldType) {
        case T_STOP:
            break;
        case T_VOID:
            continue;
        case T_BOOL:
        // case T_BYTE: would be a dupe
        case T_I08:
            CHECK_LEN(off, len, 1);
            if(fieldId >= 0) {
                tm->fields[fieldId].val_len = 1;
                tm->fields[fieldId].val_ptr = ptr + off;
                tm->fields[fieldId].val_val = (int) ptr[off];
            }
            off += 1;
            break;
        case T_I16:
            CHECK_LEN(off, len, 2);
            if(fieldId >= 0) {
                short s;
                tm->fields[fieldId].val_len = 2;
                tm->fields[fieldId].val_ptr = ptr + off;
                memcpy(&s, ptr + off, 2);
                tm->fields[fieldId].val_val = (int) ntohs(s);
            }
            off += 2;
            break;
        case T_I32:
            CHECK_LEN(off, len, 4);
            if(fieldId >= 0) {
                int i;
                tm->fields[fieldId].val_len = 4;
                tm->fields[fieldId].val_ptr = ptr + off;
                memcpy(&i, ptr + off, 4);
                tm->fields[fieldId].val_val = ntohl(i);
            }
            off += 4;
            break;
        case T_U64:
        case T_I64:
        case T_DOUBLE:
            CHECK_LEN(off, len, 8);
            if(fieldId >= 0) {
                tm->fields[fieldId].val_len = 8;
                tm->fields[fieldId].val_ptr = ptr + off;
            }
            off += 8;
            break;
            
        // Treat all of these as just length-delimited
        case T_STRING:
        // case T_UTF7: duplicate
        case T_STRUCT:
        case T_MAP:
        case T_SET:
        case T_LIST:
        case T_UTF8:
        case T_UTF16:
            if(fieldId >= 0) {
                READ_STRING(ptr, off, len, tm->fields[fieldId].val_len,
                            tm->fields[fieldId].val_ptr);
            }
            else
            {
                char *p_ign;
                int l_ign;
                READ_STRING(ptr, off, len, l_ign, p_ign);
            }
            break;
        }
    }

    return off;
too_short:
    return 0;
}
Пример #3
0
static
void
readBuffer( MeshesVector& meshes,
            FILE*     f,
            const std::string& fn )
{
    int32_t meshIndex;
//    READ_I32( meshIndex );
    if ( fread( &meshIndex, 4, 1, f ) != 1 )
    {
        if ( feof( f ) )
        {
            return; // no error, file ended
        }
        else
        {
            throw std::runtime_error( "Can't read meshIndex" + std::string(" from ") + fn );
        }
    }

    MeshData* m = meshes[ meshIndex ].get();

    int bufferType;
    int bufferSize;

    READ_I32( bufferType );
    READ_I32( bufferSize );

#define CASE( _type, _name, _data_type )                \
        case BT_##_type:                                \
            m->_name = new _data_type( bufferSize );    \
            READ( m->_name );                           \
            break

//     printf( "reading %d mesh, buffer type = %d (0x%08X), buffer size = %d\n",
//             meshIndex, bufferType, bufferType, bufferSize );
//     fflush( stdout );
    
    switch ( bufferType & BT_MASK )
    {
        case BT_INDEX:
            switch ( bufferType & ET_MASK )
            {
                case ET_UBYTE:
                    m->indexBuffer = new osg::DrawElementsUByte( osg::PrimitiveSet::TRIANGLES, bufferSize );
                    break;

                case ET_USHORT:
                    m->indexBuffer = new osg::DrawElementsUShort( osg::PrimitiveSet::TRIANGLES, bufferSize );
                    break;

                case ET_UINT:
                    m->indexBuffer = new osg::DrawElementsUInt( osg::PrimitiveSet::TRIANGLES, bufferSize );
                    break;

                default:
                {
                    char err[ 1024 ];
                    sprintf( err, "Unknown index buffer element type %d (0x%08X)",
                             bufferType & ET_MASK, bufferType & ET_MASK );
                    throw std::runtime_error( err );
                }

            }
            READ( m->indexBuffer );
            break;

        CASE( VERTEX, vertexBuffer, VertexBuffer );
        CASE( WEIGHT, weightBuffer, WeightBuffer );
        CASE( MATRIX_INDEX, matrixIndexBuffer, MatrixIndexBuffer );
        CASE( NORMAL, normalBuffer, NormalBuffer );
        CASE( TEX_COORD, texCoordBuffer, TexCoordBuffer );
        CASE( TANGENT_AND_HANDEDNESS, tangentAndHandednessBuffer, TangentAndHandednessBuffer );

        default:
        {
            char err[ 1024 ];
            sprintf( err, "Unknown buffer type %d (0x%08X)", bufferType, bufferType );
            throw std::runtime_error( err );
        }
    }

#undef CASE
}