//-------------------------------------------
bool ofxAssimpModelLoader::loadModel(ofBuffer & buffer, bool optimize, const char * extension){
	normalizeFactor = ofGetWidth() / 2.0;

	// only ever give us triangles.
	aiSetImportPropertyInteger(AI_CONFIG_PP_SBP_REMOVE, aiPrimitiveType_LINE | aiPrimitiveType_POINT );
	aiSetImportPropertyInteger(AI_CONFIG_PP_PTV_NORMALIZE, true);

	// aiProcess_FlipUVs is for VAR code. Not needed otherwise. Not sure why.
	unsigned int flags = aiProcessPreset_TargetRealtime_MaxQuality | aiProcess_Triangulate | aiProcess_FlipUVs;
	if(optimize) flags |=  aiProcess_ImproveCacheLocality | aiProcess_OptimizeGraph |
			aiProcess_OptimizeMeshes | aiProcess_JoinIdenticalVertices |
			aiProcess_RemoveRedundantMaterials;

	if(scene){
		clear();
	}
	scene = aiImportFileFromMemory(buffer.getBinaryBuffer(), buffer.size(), flags, extension);
	if(scene){
		calculateDimensions();
		loadGLResources();

		if(getAnimationCount())
			ofLog(OF_LOG_VERBOSE, "scene has animations");
		else {
			ofLog(OF_LOG_VERBOSE, "no animations");

		}
		return true;
	}else{
		ofLog(OF_LOG_ERROR,string("ofxAssimpModelLoader: ") + aiGetErrorString());
		return false;
	}

}
Пример #2
0
bool Scene::load(const ofBuffer& buffer, bool optimize, Handedness handness, const char* extension) {
	unload();

	unsigned int flags = aiProcessPreset_TargetRealtime_MaxQuality;

	if (optimize) {
		flags |= aiProcess_ImproveCacheLocality | 
				 aiProcess_JoinIdenticalVertices |
				 aiProcess_RemoveRedundantMaterials;
	}

	if (handness == LEFT_HANDED) {
		flags |= aiProcess_ConvertToLeftHanded;
	}

	scene = aiImportFileFromMemory(buffer.getBinaryBuffer(), buffer.size(),
								   flags, extension);
	string err_str = aiGetErrorString();
	if (!err_str.empty())
	{
		ofLogError("ofxAssimp::Scene::load") << err_str;
	}
	assert(scene);
	
	setupResources();
	setupNodes();
	setupAnimations();

	return true;
}
bool ofxAssimpModelLoader::processScene() {
    
    normalizeFactor = ofGetWidth() / 2.0;
    
    if(scene){
        loadGLResources();
        update();
        calculateDimensions();
        
        if(getAnimationCount())
            ofLogVerbose("ofxAssimpModelLoader") << "loadModel(): scene has " << getAnimationCount() << "animations";
        else {
            ofLogVerbose("ofxAssimpModelLoader") << "loadMode(): no animations";
        }
        
        ofAddListener(ofEvents().exit,this,&ofxAssimpModelLoader::onAppExit);
        
        
        return true;
    }else{
        ofLogError("ofxAssimpModelLoader") << "loadModel(): " + (string) aiGetErrorString();
        clear();
        return false;
    }
    
    return false;
}
Пример #4
0
Scene * AssimpSceneLoader::load(const std::string & filename, const reflectionzeug::Variant & options, std::function<void(int, int)> /*progress*/) const
{
    bool smoothNormals = false;

    // Get options
    const reflectionzeug::VariantMap * map = options.asMap();
    if (map) {
        if (map->count("smoothNormals") > 0) smoothNormals = map->at("smoothNormals").value<bool>();
    }

    // Import scene
    auto assimpScene = aiImportFile(
        filename.c_str(),
        aiProcess_Triangulate           |
        aiProcess_JoinIdenticalVertices |
        aiProcess_SortByPType |
        (smoothNormals ? aiProcess_GenSmoothNormals : aiProcess_GenNormals));

    // Check for errors
    if (!assimpScene)
    {
        std::cout << aiGetErrorString();
        return nullptr;
    }

    // Convert scene into gloperate scene
    Scene * scene = convertScene(assimpScene);

    // Release scene
    aiReleaseImport(assimpScene);

    // Return loaded scene
    return scene;
}
Пример #5
0
	Ptr<Mesh> Mesh::AssimpLoader::Load(const String& path)
	{
		auto exceptionManager = ExceptionManager::GetInstance();
		this->path = &path;
		this->dir = path.SubString(0, path.LastIndexOf(TEXT('/')));

		Assimp::Importer importer;
		const aiScene* aiscene = importer.ReadFile(path.ToStdString(),
			aiProcess_MakeLeftHanded | aiProcess_Triangulate | aiProcess_CalcTangentSpace
			| aiProcess_GenNormals | aiProcess_ValidateDataStructure | aiProcess_ImproveCacheLocality
			| aiProcess_RemoveRedundantMaterials | aiProcess_FindDegenerates | aiProcess_SortByPType
			| aiProcess_FindInvalidData | aiProcess_GenUVCoords | aiProcess_TransformUVCoords
			| aiProcess_OptimizeMeshes | aiProcess_FixInfacingNormals
			| aiProcess_JoinIdenticalVertices | aiProcess_PreTransformVertices);
		if (aiscene == nullptr)
		{
			exceptionManager->PushException(Ptr<Exception>::New(aiGetErrorString()));
			return nullptr;
		}

		Ptr<Mesh> mesh = this->LoadAssimpNode(aiscene->mRootNode, aiscene);
		if (mesh == nullptr)
			return nullptr;
		mesh->filePath = path;
		return mesh;
	}
Пример #6
0
node3d* load_model(char* path){
	struct aiScene* scene;
	printf("Loading file - %s\n", path);
	scene = aiImportFile(path, aiProcessPreset_TargetRealtime_MaxQuality);
	if(scene == NULL){
		printf("file - %s - failed to load:\n\t%s\n", path, aiGetErrorString());
		return NULL;
	} else {
		printf("file - %s - loaded.\n", path);
	}
	print_scene_data(scene);
	node3d* p_n3d = node3d_create();
	p_n3d->mesh->num_meshes = scene->mNumMeshes;
	//printf("New node has %i meshes.\n", p_n3d->mesh->num_meshes);
	p_n3d->mesh->mesh_offsets = calloc(scene->mNumMeshes, sizeof(unsigned int));
	int i, j;
	int mesh_size = 0;
	for(i = 0; i < scene->mNumMeshes; i++){
		mesh_size += scene->mMeshes[i]->mNumVertices;
	}
	int base = 0;
	//printf("Total num mesh vertices = %i\n", mesh_size);
	p_n3d->mesh->num_vertices = mesh_size * 3;
	p_n3d->mesh->vertex_data = malloc(mesh_size * 3 * sizeof(float));
	memset(p_n3d->mesh->vertex_data, 1.0, mesh_size * 3 * sizeof(float));
	for(i = 0; i < scene->mNumMeshes; i++){
		//printf("loading mesh num %i.\n", i);
		for(j = 0; j < scene->mMeshes[i]->mNumVertices; j++){
			int index = (base + j) * 3;
			vec4d res, ai_base;
			ai_base.x = scene->mMeshes[i]->mVertices[j].x;
			ai_base.y = scene->mMeshes[i]->mVertices[j].y;
			ai_base.z = scene->mMeshes[i]->mVertices[j].z;
			//vec4d_unit(&res, &ai_base);
			p_n3d->mesh->mesh_offsets[i] = base;
			//printf("adding to position - %i: ", index);
			p_n3d->mesh->vertex_data[index] = ai_base.x;
			//printf("vertice.x - %f,", res.x);
			p_n3d->mesh->vertex_data[index + 1] = ai_base.y;
			//printf("vertice.y - %f,", res.y);
			p_n3d->mesh->vertex_data[index + 2] = ai_base.z;
			//printf("vertice.y - %f\n", res.z);
		}
		base += scene->mMeshes[i]->mNumVertices;
		//printf("Base = %i\n", base);
	}
	/*
	for(i = 0; i < p_n3d->mesh->num_vertices; i++){
		printf("V - %f\n", p_n3d->mesh->vertex_data[i]);
	}
	*/
	node3d_gen_vao(p_n3d);
	return p_n3d;
}
Пример #7
0
Model::Model(std::string filename, bool invert) {
	//std::vector<float> vertex_data, normal_data;
	std::vector<Vertex> vertex_data;
	std::vector<unsigned int> indices_data;
    
	int pos = filename.find_last_of("/");
	if(pos == std::string::npos)
		pos = filename.find_last_of("\\");
    
	folderPath = filename.substr(0, pos + 1);
    
	scene = aiImportFile(filename.c_str(), aiProcessPreset_TargetRealtime_Quality);// | aiProcess_FlipWindingOrder);
	if (!scene) {
		std::string log = aiGetErrorString();
		THROW_EXCEPTION(log);
	}
	
	max_dim = -glm::vec3(std::numeric_limits<float>().max());
	min_dim = glm::vec3(std::numeric_limits<float>().max());
    
	//Load the model recursively into data
	loadRecursive(root, invert, indices_data, vertex_data, scene, scene->mRootNode);
    
	float tmp;
    tmp = max_dim.x - min_dim.x;
    tmp = max_dim.y - min_dim.y > tmp ? max_dim.y - min_dim.y : tmp;
    tmp = max_dim.z - min_dim.z > tmp ? max_dim.z - min_dim.z : tmp;
    float scaleFactor = 1.0f / tmp;
	
	glm::vec3 center = (max_dim + min_dim);
	center /= 2;
    
	root.transform = glm::scale(glm::mat4(1), glm::vec3(scaleFactor));
	root.transform = glm::translate(root.transform, -center);
    
	n_vertices = indices_data.size();
    
    std::cout << "Loaded model with " << n_vertices << " vertices" << std::endl;
    
	//Create the VBOs from the data.
	if (fmod(static_cast<float>(n_vertices), 3.0f) < 0.000001f)
	{
		indices.reset(new GLUtils::BO<GL_ELEMENT_ARRAY_BUFFER>(indices_data.data(), indices_data.size() * sizeof(unsigned int)));
		vertices.reset(new GLUtils::BO<GL_ARRAY_BUFFER>(vertex_data.data(), vertex_data.size() * sizeof(Vertex)));
        
        std::cout << "Created and uploaded VBOs" << std::endl;
	}
	else
	{
		THROW_EXCEPTION("The number of vertices in the mesh is wrong");
	}
}
Пример #8
0
//------------------------------------------
bool ofxAssimpModelLoader::loadModel(string modelName, unsigned extraFlags /* = 0 */){


    // if we have a model loaded, unload the f****r.
    if(scene != NULL){
        clear();
    }

    // Load our new path.
    filepath = modelName;
    string filepath = ofToDataPath(modelName);

	//theo added - so we can have models and their textures in sub folders
	modelFolder = ofFilePath::getEnclosingDirectory(filepath);

    ofLog(OF_LOG_VERBOSE, "loading model %s", filepath.c_str());
    ofLog(OF_LOG_VERBOSE, "loading from folder %s", modelFolder.c_str());

    // only ever give us triangles.
    aiSetImportPropertyInteger(AI_CONFIG_PP_SBP_REMOVE, aiPrimitiveType_LINE | aiPrimitiveType_POINT );
    aiSetImportPropertyInteger(AI_CONFIG_PP_PTV_NORMALIZE, true);

    // aiProcess_FlipUVs is for VAR code. Not needed otherwise. Not sure why.
    unsigned int flags = aiProcessPreset_TargetRealtime_MaxQuality | aiProcess_Triangulate | aiProcess_FlipUVs;
	flags |= extraFlags;
	/*
    if(optimize) flags |=  aiProcess_ImproveCacheLocality | aiProcess_OptimizeGraph |
			aiProcess_OptimizeMeshes | aiProcess_JoinIdenticalVertices |
			aiProcess_RemoveRedundantMaterials;
	*/

    scene = aiImportFile(filepath.c_str(), flags);

    if(scene){
        calculateDimensions();
        loadGLResources();

        if(getAnimationCount())
            ofLog(OF_LOG_VERBOSE, "scene has animations");
        else {
            ofLog(OF_LOG_VERBOSE, "no animations");

        }
		collectNodeTransforms(scene, scene->mRootNode);
		collectBoneTransforms();

        return true;
    }else{
    	ofLog(OF_LOG_ERROR,string("ofxAssimpModelLoader: ") + aiGetErrorString());
    	return false;
    }
}
Пример #9
0
/* \brief import Assimp file */
int _glhckImportAssimp(glhckObject *object, const char *file, const glhckImportModelParameters *params,
                       glhckGeometryIndexType itype, glhckGeometryVertexType vtype)
{
    const struct aiScene *scene;
    glhckObject *first = NULL;
    unsigned int aflags;
    CALL(0, "%p, %s, %p", object, file, params);

    /* import the model using assimp
     * TODO: make import hints tunable?
     * Needs changes to import protocol! */
    aflags = aiProcessPreset_TargetRealtime_Fast | aiProcess_OptimizeGraph;
    if (!params->animated && params->flatten) aflags |= aiProcess_PreTransformVertices;
    scene = aiImportFile(file, aflags);
    if (!scene) goto assimp_fail;

    /* mark ourself as special root object.
     * this makes most functions called on root object echo to children */
    object->flags |= GLHCK_OBJECT_ROOT;

    /* this is going to be the first object in mesh,
     * the object returned by this importer is just invisible root object. */
    if (!(first = glhckObjectNew())) goto fail;
    glhckObjectAddChild(object, first);
    glhckObjectFree(first);

    /* process the model */
    if (processModel(file, object, first, scene, scene->mRootNode,
                     itype, vtype, params) != RETURN_OK)
        goto fail;

    /* process the animated model part */
    if (params->animated && processBonesAndAnimations(object, scene) != RETURN_OK)
        goto fail;

    /* close file */
    NULLDO(aiReleaseImport, scene);
    RET(0, "%d", RETURN_OK);
    return RETURN_OK;

assimp_fail:
    DEBUG(GLHCK_DBG_ERROR, aiGetErrorString());
fail:
    IFDO(aiReleaseImport, scene);
    IFDO(glhckObjectFree, first);
    RET(0, "%d", RETURN_FAIL);
    return RETURN_FAIL;
}
Пример #10
0
void load_mesh(char* fname, state_t* state, transform_data_t t, int bsdf_index, char* matname) {

	printf("Loading mesh %s\n",fname);

	//parse file
	const aiScene* scene = aiImportFile(fname, aiProcess_Triangulate | aiProcess_JoinIdenticalVertices);

	qr_assert(scene, "parser", "Could not open mesh file: %s (%s)",fname, aiGetErrorString());
	
	for(int i=0; i<scene->mNumMeshes; i++) {
		bool contin = false;

		if(matname == NULL) {
			contin = true;
		}
		else {
			aiString name;
			aiGetMaterialString(scene->mMaterials[scene->mMeshes[i]->mMaterialIndex], AI_MATKEY_NAME, &name);
			contin = strcmp(matname, &name.data[0]) == 0;
		}

		if(contin) {
			int pind = state->n_primitives;
			state->n_primitives += scene->mMeshes[i]->mNumFaces;
			state->primitives = (primitive_t*)realloc(state->primitives, sizeof(primitive_t)*(state->n_primitives));
			int vind = state->n_verts;
			int vstart = state->n_verts;
			state->n_verts += scene->mMeshes[i]->mNumVertices;
			state->verts = (vec3*)realloc(state->verts, sizeof(vec3)*(state->n_verts));

			for(int j=0; j<scene->mMeshes[i]->mNumVertices; j++) {
				state->verts[vind++] = transform_point(make_vec3(scene->mMeshes[i]->mVertices[j].x, scene->mMeshes[i]->mVertices[j].y, scene->mMeshes[i]->mVertices[j].z), state->transforms[t.index], false);
			}

			for(int j=0; j<scene->mMeshes[i]->mNumFaces; j++) {
				qr_assert(scene->mMeshes[i]->mFaces[j].mNumIndices==3, "parser", "Only triangles are supported (%s)",fname);
				state->primitives[pind].type = PRIMITIVE_TRIANGLE;
				state->primitives[pind].t = 0;
				state->primitives[pind].bsdf = bsdf_index;
				state->primitives[pind++].data = make_primitive_triangle(vstart+scene->mMeshes[i]->mFaces[j].mIndices[0], vstart+scene->mMeshes[i]->mFaces[j].mIndices[1], vstart+scene->mMeshes[i]->mFaces[j].mIndices[2]);
			}
		}
	}

	aiReleaseImport(scene);
}
Пример #11
0
static int assimp_import_file(lua_State *L) {
	const char *filename = luaX_checkstring(L, 1, "filename");
	unsigned int flags = luaX_checkinteger(L, 2, "flags");

	struct aiScene *scene = (struct aiScene*)aiImportFile(filename, flags);
	if (scene == NULL) {
		lua_pushnil(L);                                    // [-0,+1,-]
		lua_pushstring(L, aiGetErrorString());             // [-0,+1,e]

		return 2;
	}

	_make_scene(L, scene);                               // [-0,+1,e]

	aiReleaseImport(scene);

	return 1;
}
Пример #12
0
bool ImportedModel::load(string filename)
{
    bool ret = false;

	const aiScene* scene = aiImportFile(filename.c_str(), aiProcess_GenSmoothNormals | aiProcess_Triangulate | aiProcess_CalcTangentSpace | aiProcess_FlipUVs);

	if (scene)
	{
		m_aabb.min = glm::vec3(INT_MAX);
		m_aabb.max = glm::vec3(INT_MIN);

	//	cout << "Loading " << filename << endl;
		ret = initFromAiScene(scene, filename);
	}
	else
        cout << "Error parsing '"<< filename.c_str() << "': '" << aiGetErrorString() << endl;


    return ret;
}
Пример #13
0
static int assimp_export_scene(lua_State *L) {
	luaX_checktype(L, 1, "scene", LUA_TTABLE);
	const char *format = luaX_checkstring(L, 2, "format");
	const char *filename = luaX_checkstring(L, 3, "filename");

	struct aiScene *scene = _convert_scene(L, 1);

	if (aiExportScene(scene, format, filename, 0)) {
		aiReleaseImport(scene);
		lua_pushboolean(L, true);                          // [-0,+1,-]
	}
	else {
		aiReleaseImport(scene);
		lua_pushboolean(L, false);                         // [-0,+1,-]
		lua_pushstring(L, aiGetErrorString());             // [-0,+1,e]

		return 2;
	}

	return 1;
}
//-------------------------------------------
bool ofxAssimpModelLoader::loadModel(ofBuffer & buffer, bool optimize, const char * extension){
	normalizeFactor = ofGetWidth() / 2.0;
    
    if(scene != NULL){
        clear();
    }
    
	// only ever give us triangles.
	aiSetImportPropertyInteger(AI_CONFIG_PP_SBP_REMOVE, aiPrimitiveType_LINE | aiPrimitiveType_POINT );
	aiSetImportPropertyInteger(AI_CONFIG_PP_PTV_NORMALIZE, true);

	// aiProcess_FlipUVs is for VAR code. Not needed otherwise. Not sure why.
	unsigned int flags = aiProcessPreset_TargetRealtime_MaxQuality | aiProcess_Triangulate | aiProcess_FlipUVs;
	if(optimize) flags |=  aiProcess_ImproveCacheLocality | aiProcess_OptimizeGraph |
			aiProcess_OptimizeMeshes | aiProcess_JoinIdenticalVertices |
			aiProcess_RemoveRedundantMaterials;

	scene = aiImportFileFromMemory(buffer.getBinaryBuffer(), buffer.size(), flags, extension);
    
	if(scene){
		calculateDimensions();
		loadGLResources();
        update();

		if(getAnimationCount())
			ofLogVerbose("ofxAssimpModelLoader") << "loadModel(): scene has " << getAnimationCount() << "animations";
		else {
			ofLogVerbose("ofxAssimpModelLoader") << "loadMode(): no animations";
		}

		ofAddListener(ofEvents().exit,this,&ofxAssimpModelLoader::onAppExit);


		return true;
	}else{
		ofLogError("ofxAssimpModelLoader") << "loadModel(): " + (string) aiGetErrorString();
		clear();
		return false;
	}
}
Пример #15
0
PolygonalGeometry * AssimpMeshLoader::load(const std::string & filename, const reflectionzeug::Variant & options, std::function<void(int, int)> /*progress*/) const
{
    bool smoothNormals = false;

    // Get options
    const reflectionzeug::VariantMap * map = options.asMap();
    if (map) {
        if (map->count("smoothNormals") > 0) smoothNormals = map->at("smoothNormals").value<bool>();
    }

    // Import scene
    auto scene = aiImportFile(
        filename.c_str(),
        aiProcess_Triangulate           |
        aiProcess_JoinIdenticalVertices |
        aiProcess_SortByPType |
        (smoothNormals ? aiProcess_GenSmoothNormals : aiProcess_GenNormals));

    // Check for errors
    if (!scene)
    {
        std::cout << aiGetErrorString();
        return nullptr;
    }

    // Convert first mesh found in the scene
    PolygonalGeometry * geometry = nullptr;
    if (scene->mNumMeshes > 0) {
        geometry = convertGeometry(scene->mMeshes[0]);
    }

    // Release scene
    aiReleaseImport(scene);

    // Return loaded mesh
    return geometry;
}
Пример #16
0
int import_anim(const struct import_params* params)
{
    uint flags = 0;
    if (params->coord == COORD_NONE)
        flags |= aiProcess_MakeLeftHanded;

    const struct aiScene* scene = aiImportFileEx(params->in_filepath, flags, NULL);

    if (scene == NULL)  {
        printf(TERM_BOLDRED "Error: (assimp) %s\n" TERM_RESET, aiGetErrorString());
        return FALSE;
    }

    if (scene->mNumAnimations == 0) {
        printf(TERM_BOLDRED "Error: no animation exist in the file '%s'" TERM_RESET,
            params->in_filepath);
        return FALSE;
    }

    g_anim_coord = params->coord;
    uint fps = params->anim_fps != 0 ? params->anim_fps : DEFAULT_FPS;
    uint channel_cnt = 0;
    uint frame_cnt = 0;
    int has_scale = FALSE;

    /* channel count is the sum of all animation channels */
    /* frame_cnt is the maximum of all animation channel key counts */
    for (uint i = 0; i < scene->mNumAnimations; i++)  {
        const struct aiAnimation* anim = scene->mAnimations[i];
        channel_cnt += anim->mNumChannels;
        for (uint k = 0; k < anim->mNumChannels; k++) {
            frame_cnt = maxui(frame_cnt, maxui(anim->mChannels[k]->mNumPositionKeys,
                maxui(anim->mChannels[k]->mNumRotationKeys, anim->mChannels[k]->mNumScalingKeys)));
        }
    }

    if (channel_cnt == 0)   {
        printf(TERM_BOLDRED "Error: no animation channels exist in the file '%s'" TERM_RESET,
            params->in_filepath);
        return FALSE;
    }

    /* parse my data from assimp data */
    struct anim_ext h3danim;
    memset(&h3danim, 0x00, sizeof(h3danim));

    /* channels */
    struct anim_channel_ext* h3dchannels = (struct anim_channel_ext*)
        ALLOC(sizeof(struct anim_channel_ext)*channel_cnt, 0);
    ASSERT(h3dchannels != NULL);
    memset(h3dchannels, 0x00, sizeof(struct anim_channel_ext)*channel_cnt);

    uint channel_offset = 0;
    for (uint i = 0; i < scene->mNumAnimations; i++)  {
        struct aiAnimation* anim = scene->mAnimations[i];

        for (uint k = 0; k < anim->mNumChannels; k++) {
            struct aiNodeAnim* channel = anim->mChannels[k];
            struct anim_channel_ext* h3dchannel = &h3dchannels[k + channel_offset];

            str_safecpy(h3dchannel->c.bindto, sizeof(h3dchannel->c.bindto), channel->mNodeName.data);
            h3dchannel->pos_scale = (struct vec4f*)ALLOC(sizeof(struct vec4f)*frame_cnt, 0);
            h3dchannel->rot = (struct quat4f*)ALLOC(sizeof(struct quat4f)*frame_cnt, 0);
            ASSERT(h3dchannel->pos_scale && h3dchannel->rot);

            struct vec3f pos;
            struct quat4f quat;
            float scale = 1.0f;

            /* fill channel data */
            for (uint f = 0; f < frame_cnt; f++)  {
                if (f < channel->mNumPositionKeys)  {
                    vec3_setf(&pos,
                        channel->mPositionKeys[f].mValue.x,
                        channel->mPositionKeys[f].mValue.y,
                        channel->mPositionKeys[f].mValue.z);
                }

                if (f < channel->mNumRotationKeys)  {
                    quat_setf(&quat,
                        channel->mRotationKeys[f].mValue.x,
                        channel->mRotationKeys[f].mValue.y,
                        channel->mRotationKeys[f].mValue.z,
                        channel->mRotationKeys[f].mValue.w);
                }

                if (f < channel->mNumScalingKeys)   {
                    scale = (channel->mScalingKeys[f].mValue.x +
                        channel->mScalingKeys[f].mValue.y +
                        channel->mScalingKeys[f].mValue.z) / 3.0f;
                    has_scale |= !math_isequal(scale, 1.0f);
                }

                import_convert_vec3(&pos, &pos, g_anim_coord);
                import_convert_quat(&quat, &quat, g_anim_coord);

                vec4_setf(&h3dchannel->pos_scale[f], pos.x, pos.y, pos.z, scale);
                quat_setf(&h3dchannel->rot[f], quat.x, quat.y, quat.z, quat.w);
            }
        }

        channel_offset += anim->mNumChannels;
    }

    /* write to file */
    h3danim.a.channel_cnt = channel_cnt;
    h3danim.a.frame_cnt = frame_cnt;
    h3danim.a.has_scale = has_scale;
    h3danim.a.fps = fps;
    h3danim.channels = h3dchannels;

    /* parse json clip file */
    h3danim.clips = import_loadclips(params->clips_json_filepath, frame_cnt, &h3danim.a.clip_cnt);

    /* write */
    int r = import_writeanim(params->out_filepath, &h3danim);

    /* report */
    if (r)  {
        printf(TERM_BOLDGREEN "ok, saved: \"%s\".\n" TERM_RESET, params->out_filepath);

        if (params->verbose)    {
            printf(TERM_WHITE);
            printf("Animation report:\n"
                "  animation count: %d\n"
                "  frame count: %d\n"
                "  channel count: %d\n"
                "  has_scale: %s\n"
                "  fps: %d\n",
                scene->mNumAnimations,
                frame_cnt,
                channel_cnt,
                has_scale ? "yes" : "no",
                fps);
            printf(TERM_RESET);
        }
    }

    /* cleanup */
    for (uint i = 0; i < h3danim.a.channel_cnt; i++)    {
        if (h3danim.channels[i].pos_scale != NULL)
            FREE(h3danim.channels[i].pos_scale);
        if (h3danim.channels[i].rot != NULL)
            FREE(h3danim.channels[i].rot);
    }
    FREE(h3danim.clips);
    FREE(h3danim.channels);
    aiReleaseImport(scene);

    return r;
}
Пример #17
0
//data loading
bool ModelData::LoadIn(QString filepath)
{	
    unsigned int m;
    unsigned int t;
    unsigned int i;

    Triangle3D newtri;
    const struct aiFace* face;

	
	this->filepath = filepath;
	
	if(filepath.isEmpty())
		return false;
	
	//extract filename from path!
	filename = QFileInfo(filepath).baseName();

	//AI_CONFIG_PP_FD_REMOVE = aiPrimitiveType_POINTS | aiPrimitiveType_LINES;
    pScene = aiImportFile(filepath.toAscii(), aiProcess_Triangulate);// | aiProcess_JoinIdenticalVertices); //trian
	
    if(pScene == NULL)//assimp cant handle the file - lets try our own reader.
	{
		//display Assimp Error
		QMessageBox msgBox;
		msgBox.setText("Assimp Error:  " + QString().fromAscii(aiGetErrorString()));
		msgBox.exec();

        aiReleaseImport(pScene);

		return false;
	}

    qDebug() << "Model imported with " << pScene->mMeshes[0]->mNumFaces << " faces.";
	

	for (m = 0; m < pScene->mNumMeshes; m++) 
	{
		const aiMesh* mesh = pScene->mMeshes[m];
		
	    for (t = 0; t < mesh->mNumFaces; t++)
		{
            face = &mesh->mFaces[t];
			
			if(face->mNumIndices == 3)
			{
				for(i = 0; i < face->mNumIndices; i++) 
				{
					int index = face->mIndices[i];
				
                    newtri.normal.setX(mesh->mNormals[index].x);
                    newtri.normal.setY(mesh->mNormals[index].y);
                    newtri.normal.setZ(mesh->mNormals[index].z);
			
                    newtri.vertex[i].setX(mesh->mVertices[index].x);
                    newtri.vertex[i].setY(mesh->mVertices[index].y);
                    newtri.vertex[i].setZ(mesh->mVertices[index].z);
				}
                newtri.UpdateBounds();
                triList.push_back(newtri);

			}
		}
	}

    aiReleaseImport(pScene);

    qDebug() << "Loaded triangles: " << triList.size();
	//now center it!
	CenterModel();

	//generate a displaylist
    int displayerror = FormDisplayList();

    //check for errors in display list creation (if its a large model the card may run out of memory.

    if(displayerror){
    while(displayerror)//loop and see if there are additional errors as well.
    {
        //display Assimp Error
        qDebug() << "Display List Error: " << displayerror; //write to log as well.
        QMessageBox msgBox;

        switch(displayerror)
        {
        case GL_OUT_OF_MEMORY:
            msgBox.setText("OpenGL Error:  GL_OUT_OF_MEMORY\nModel is too large to render on your graphics card.");
            break;
        case GL_INVALID_ENUM:
            msgBox.setText("OpenGL Error:  GL_INVALID_ENUM");
            break;
        case GL_INVALID_VALUE:
            msgBox.setText("OpenGL Error:  GL_INVALID_VALUE");
            break;
        case GL_INVALID_FRAMEBUFFER_OPERATION:
            msgBox.setText("OpenGL Error:  GL_INVALID_FRAMEBUFFER_OPERATION");
            break;
        case GL_STACK_UNDERFLOW:
            msgBox.setText("OpenGL Error:  GL_STACK_UNDERFLOW");
            break;
        case GL_STACK_OVERFLOW:
            msgBox.setText("OpenGL Error:  GL_STACK_OVERFLOW");
            break;
        default:
            break;
        }

        msgBox.exec();
        displayerror = glGetError();
    }
    return false;
    }




	return true;
}
Пример #18
0
void mjAssimpModel::LoadFromFile(const char* fileName)
{
    mjMatrixStack* matrixStack = new mjMatrixStack();
    scene = aiImportFile(fileName,aiProcessPreset_TargetRealtime_MaxQuality);

    if (scene)
    {
        for (int i = 0; i < scene->mNumMaterials; i++)
        {
            // Keep trying to extract textures until it fails
            aiString textureFilename;

            aiMaterial* mat = scene->mMaterials[i];

            aiReturn textureFilenameWasExtracted;
            int diffuseTextureIndex = 0;

            do
            {
                textureFilenameWasExtracted = mat->GetTexture(aiTextureType_DIFFUSE, diffuseTextureIndex, &textureFilename);
                if (textureFilenameWasExtracted == AI_SUCCESS)
                {
                    // Load using the manager.

                    //FIXME: For now only the first texture is used :3

                    if (diffuseTextureIndex == 0)
                    {
                        std::string texFilenameWithoutJunk = textureFilename.C_Str();
                        int lastDirChar = texFilenameWithoutJunk.find_last_of('/');
                        int lastInvertDirChar = texFilenameWithoutJunk.find_last_of('\\');
                        if (lastInvertDirChar > lastDirChar)
                        {
                            lastDirChar = lastInvertDirChar;
                        }
                        texFilenameWithoutJunk = texFilenameWithoutJunk.substr(lastDirChar+1);
                        glTextureForMaterial.push_back(resManager->FetchTexture(texFilenameWithoutJunk, GL_REPEAT));
                    }
                }
                diffuseTextureIndex++;
            } while (textureFilenameWasExtracted == AI_SUCCESS);

        }


        // Now build the internal data structures ( structure, drawOrderBuffers, etc.)


        for (unsigned i = 0; i < scene->mNumMeshes; i++)
        {
            meshes.push_back(NULL);
        }



        aiNode* node = scene->mRootNode;


        RecursiveBuild(node, matrixStack);
    } else
    {
        LOGI("Assimp import error: %s", aiGetErrorString());
    }
    delete matrixStack;
}
Пример #19
0
int nilerrmsg(lua_State *L)
    {
    lua_pushnil(L); 
    lua_pushstring(L, aiGetErrorString()); 
    return 2;
    }
Пример #20
0
int main(int argc, char **argv)
{
	FILE *file;
	const struct aiScene *scene;
	char *p;
	int c;

	char *output = NULL;
	char *input = NULL;
	int onlyanim = 0;
	int onlymesh = 0;

	while ((c = getopt(argc, argv, "AHMPSabflmn:o:rvxsu:")) != -1) {
		switch (c) {
		case 'A': save_all_bones++; break;
		case 'H': dohips = 1; break;
		case 'M': list_all_meshes = 1; break;
		case 'P': list_all_positions = 1; break;
		case 'S': dostatic = 1; break;
		case 'a': onlyanim = 1; break;
		case 'm': onlymesh = 1; break;
		case 'n': only_one_node = optarg++; break;
		case 'b': need_to_bake_skin = 1; break;
		case 'o': output = optarg++; break;
		case 'f': doflip = 0; break;
		case 'r': dorigid = 1; break;
		case 'l': dolowprec = 1; break;
		case 'v': verbose++; break;
		case 'x': doaxis = 1; break;
		case 's': dounscale = 1; break;
		case 'u': untaglist[numuntags++] = optarg++; break;
		default: usage(); break;
		}
	}

	if (optind == argc)
		usage();

	input = argv[optind++];

	p = strrchr(input, '/');
	if (!p) p = strrchr(input, '\\');
	if (!p) p = input; else p++;
	strcpy(basename, p);
	p = strrchr(basename, '.');
	if (p) *p = 0;

	numtags = argc - optind;
	taglist = argv + optind;

	/* Read input file and post process */

	int flags = 0;
	flags |= aiProcess_JoinIdenticalVertices;
	flags |= aiProcess_GenSmoothNormals;
	flags |= aiProcess_GenUVCoords;
	flags |= aiProcess_TransformUVCoords;
	flags |= aiProcess_LimitBoneWeights;
	//flags |= aiProcess_FindInvalidData;
	flags |= aiProcess_ImproveCacheLocality;
	//flags |= aiProcess_RemoveRedundantMaterials;
	//flags |= aiProcess_OptimizeMeshes;

	fprintf(stderr, "loading %s\n", input);
	scene = aiImportFile(input, flags);
	if (!scene) {
		fprintf(stderr, "cannot import '%s': %s\n", input, aiGetErrorString());
		exit(1);
	}

	if (scene->mNumAnimations > 0) doanim = 1;
	if (onlymesh) { domesh = 1; doanim = 0; }
	if (onlyanim) { domesh = 0; doanim = 1; }

	if (getenv("DOANIM")) doanim = 1;

	// Convert to Z-UP coordinate system
	aiMultiplyMatrix4(&scene->mRootNode->mTransformation, &yup_to_zup);

	// Build a list of bones and compute the bind pose matrices.
	if (build_bone_list(scene) > 0)
		dobone = 1;

	if (dostatic) {
		dobone = 0;
		need_to_bake_skin = 0;
	}

	if (list_all_meshes) {
		export_mesh_list(scene);
		return 0;
	}

	if (list_all_positions) {
		export_position_list(scene);
		return 0;
	}

	// Mesh is split with incompatible bind matrices, so pick a new
	// bind pose and deform the mesh to fit.
	if (need_to_bake_skin && !onlyanim) {
		apply_initial_frame(); // ditch original bind pose
		bake_scene_skin(scene);
	}

	/*
	 * Export scene as mesh/skeleton/animation
	 */

	if (output) {
		fprintf(stderr, "saving %s\n", output);
		file = fopen(output, "w");
		if (!file) {
			fprintf(stderr, "cannot open output file: '%s'\n", output);
			exit(1);
		}
	} else {
		file = stdout;
	}

	fprintf(file, "# Inter-Quake Export\n");

	if (dobone) {
		export_bone_list(file);
	}

	if (domesh) {
		struct aiMatrix4x4 identity;
		aiIdentityMatrix4(&identity);
		export_custom_vertexarrays(file, scene);
		export_node(file, scene, scene->mRootNode, identity, "SCENE");
	}

	if (dobone) {
		if (doanim) {
			export_animations(file, scene);
		}
	}

	if (output)
		fclose(file);

	aiReleaseImport(scene);

	return 0;
}