1 /* 2 * Copyright 2006 Sony Computer Entertainment Inc. 3 * 4 * Licensed under the MIT Open Source License, for details please see license.txt or the website 5 * http://www.opensource.org/licenses/mit-license.php 6 * 7 */ 8 9 #include <dae/daeRawResolver.h> 10 #include <dae.h> 11 #include <dae/daeURI.h> 12 #include <dae/daeErrorHandler.h> 13 #include <dae/daeUtils.h> 14 15 using namespace std; 16 17 daeRawResolver::daeRawResolver(DAE& dae) : daeURIResolver(dae) 18 { 19 } 20 21 daeRawResolver::~daeRawResolver() 22 { 23 } 24 25 daeString 26 daeRawResolver::getName() 27 { 28 return "RawResolver"; 29 } 30 31 daeElement* daeRawResolver::resolveElement(const daeURI& uri) { 32 if (cdom::tolower(uri.pathExt()).find(".raw") == string::npos) 33 return NULL; 34 35 daeRawRefCache& cache = dae->getRawRefCache(); 36 if (daeElement* elt = cache.lookup(uri)) 37 return elt; 38 39 string fileName = cdom::uriToNativePath(uri.str()); 40 if (fileName.empty()) 41 { 42 daeErrorHandler::get()->handleError( "daeRawResolver::resolveElement() - Can't get path from URI\n" ); 43 return NULL; 44 } 45 FILE *rawFile = fopen(fileName.c_str(), "rb"); 46 if (rawFile == NULL ) 47 return NULL; 48 long byteOffset = atoi( uri.getID() ); //get the fragment 49 50 daeElement *src; 51 daeElement *array; 52 daeElement *accessor; 53 54 accessor = uri.getContainer(); 55 if ( accessor == NULL ) 56 return NULL; 57 src = accessor->getParentElement()->getParentElement(); 58 daeElementRefArray children; 59 accessor->getChildren( children ); 60 bool hasInts = children[0]->getAttribute("type") == "int"; 61 62 if ( hasInts ) 63 { 64 array = src->createAndPlace( "int_array" ); 65 } 66 else 67 { 68 array = src->createAndPlace( "float_array" ); 69 } 70 71 daeULong *countPtr = (daeULong*)accessor->getAttributeValue( "count" ); 72 daeULong count = countPtr != NULL ? *countPtr : 0; 73 74 daeULong *stridePtr = (daeULong*)accessor->getAttributeValue( "stride" ); 75 daeULong stride = stridePtr != NULL ? *stridePtr : 1; 76 77 *(daeULong*)(array->getAttributeValue("count")) = count*stride; 78 array->setAttribute( "id", (src->getAttribute("id") + "-array").c_str() ); 79 80 daeArray *valArray = (daeArray*)array->getValuePointer(); 81 valArray->setCount( (size_t)(count*stride) ); 82 83 fseek( rawFile, byteOffset, SEEK_SET ); 84 if ( hasInts ) 85 { 86 daeInt val; 87 for ( unsigned int i = 0; i < count*stride; i++ ) 88 { 89 fread( &val, sizeof(daeInt), 1, rawFile ); 90 *(daeLong*)(valArray->getRaw(i)) = (daeLong)val; 91 } 92 } 93 else 94 { 95 daeFloat val; 96 for ( unsigned int i = 0; i < count*stride; i++ ) 97 { 98 fread( &val, sizeof(daeFloat), 1, rawFile ); 99 *(daeDouble*)(valArray->getRaw(i)) = (daeDouble)val; 100 } 101 } 102 103 fclose(rawFile); 104 cache.add(uri, array); 105 return array; 106 } 107 108 109 daeElement* daeRawRefCache::lookup(const daeURI& uri) { 110 map<string, daeElement*>::iterator iter = lookupTable.find(uri.str()); 111 return iter == lookupTable.end() ? NULL : iter->second; 112 } 113 114 void daeRawRefCache::add(const daeURI& uri, daeElement* elt) { 115 lookupTable[uri.str()] = elt; 116 } 117 118 void daeRawRefCache::remove(const daeURI& uri) { 119 lookupTable.erase(uri.str()); 120 } 121 122 void daeRawRefCache::clear() { 123 lookupTable.clear(); 124 } 125