Exemple #1
0
/**
 * Inserts a new vertex into the graph and labels it.
 * @param label the label for the vertex
 * @return a copy of the vertex that was inserted
 */
Vertex Graph::insertVertex(string label /* = "" */)
{
    Vertex vertex = nextVertex();
    graph.insert(make_pair(vertex, EdgeMap()));
    vertexLabels.insert(make_pair(vertex, label));
    return vertex;
}
Exemple #2
0
// shade a mesh
void shade_mesh(Mesh* mesh, int time, bool wireframe, bool skinning_gpu, bool draw_normals, ShadeState* state) {
    // bind material kd, ks, n
    glUniform3fv(glGetUniformLocation(state->gl_program_id,"material_kd"),
                 1,&mesh->mat->kd.x);
    glUniform3fv(glGetUniformLocation(state->gl_program_id,"material_ks"),
                 1,&mesh->mat->ks.x);
    glUniform1f(glGetUniformLocation(state->gl_program_id,"material_n"),
                mesh->mat->n);
    glUniform1i(glGetUniformLocation(state->gl_program_id,"material_is_lines"),
                GL_FALSE);
    glUniform1i(glGetUniformLocation(state->gl_program_id,"material_double_sided"),
                (mesh->mat->double_sided)?GL_TRUE:GL_FALSE);
    // bind texture params (txt_on, sampler)
    _bind_texture("material_kd_txt", "material_kd_txt_on", mesh->mat->kd_txt, 0, state);
    _bind_texture("material_ks_txt", "material_ks_txt_on", mesh->mat->ks_txt, 1, state);
    _bind_texture("material_norm_txt", "material_norm_txt_on", mesh->mat->norm_txt, 2, state);
    
    // bind mesh frame - use frame_to_matrix
    glUniformMatrix4fv(glGetUniformLocation(state->gl_program_id,"mesh_frame"),
                       1,true,&frame_to_matrix(mesh->frame)[0][0]);
    
    // enable vertex attributes arrays and set up pointers to the mesh data
    auto vertex_pos_location = glGetAttribLocation(state->gl_program_id, "vertex_pos");
    auto vertex_norm_location = glGetAttribLocation(state->gl_program_id, "vertex_norm");
    auto vertex_texcoord_location = glGetAttribLocation(state->gl_program_id, "vertex_texcoord");
    // YOUR CODE GOES HERE ---------------------
    // (only for extra credit)
    auto vertex_skin_bone_ids_location = glGetAttribLocation(state->gl_program_id, "vertex_skin_bone_ids");
    auto vertex_skin_bone_weights_location = glGetAttribLocation(state->gl_program_id, "vertex_skin_bone_weights");
    
    glEnableVertexAttribArray(vertex_pos_location);
    glVertexAttribPointer(vertex_pos_location, 3, GL_FLOAT, GL_FALSE, 0, &mesh->pos[0].x);
    glEnableVertexAttribArray(vertex_norm_location);
    glVertexAttribPointer(vertex_norm_location, 3, GL_FLOAT, GL_FALSE, 0, &mesh->norm[0].x);
    if(not mesh->texcoord.empty()) {
        glEnableVertexAttribArray(vertex_texcoord_location);
        glVertexAttribPointer(vertex_texcoord_location, 2, GL_FLOAT, GL_FALSE, 0, &mesh->texcoord[0].x);
    }
    else glVertexAttrib2f(vertex_texcoord_location, 0, 0);
    
    if (mesh->skinning and skinning_gpu) {
        // YOUR CODE GOES HERE ---------------------
        // (only for extra credit)
        glUniform1i(glGetUniformLocation(state->gl_program_id, "skin_enabled"), true);

        glEnableVertexAttribArray(vertex_skin_bone_ids_location);
        glVertexAttribPointer(vertex_skin_bone_ids_location, 4, GL_INT, GL_FALSE, 0, &mesh->skinning->bone_ids[0].x);
        
        glEnableVertexAttribArray(vertex_skin_bone_weights_location);
        glVertexAttribPointer(vertex_skin_bone_weights_location, 4, GL_FLOAT, GL_FALSE, 0, &mesh->skinning->bone_weights[0].x);

        for (int i = 0; i < 48; i++) {
            string name = "skin_bone_xforms["+std::to_string(i)+"]";
            glUniformMatrix4fv(glGetUniformLocation(state->gl_program_id, name.c_str()), 1, GL_TRUE, &mesh->skinning->bone_xforms[time][i][0].x);
        }
        
    } else {
        glUniform1i(glGetUniformLocation(state->gl_program_id,"skin_enabled"),GL_FALSE);
    }
    
    // draw triangles and quads
    if(not wireframe) {
        if(mesh->triangle.size()) glDrawElements(GL_TRIANGLES, mesh->triangle.size()*3, GL_UNSIGNED_INT, &mesh->triangle[0].x);
        if(mesh->quad.size()) glDrawElements(GL_QUADS, mesh->quad.size()*4, GL_UNSIGNED_INT, &mesh->quad[0].x);
        if(mesh->point.size()) glDrawElements(GL_POINTS, mesh->point.size(), GL_UNSIGNED_INT, &mesh->point[0]);
        if(mesh->line.size()) glDrawElements(GL_LINES, mesh->line.size(), GL_UNSIGNED_INT, &mesh->line[0].x);
        for(auto segment : mesh->spline) glDrawElements(GL_LINE_STRIP, 4, GL_UNSIGNED_INT, &segment);
    } else {
        auto edges = EdgeMap(mesh->triangle, mesh->quad).edges();
        glDrawElements(GL_LINES, edges.size()*2, GL_UNSIGNED_INT, &edges[0].x);
    }
    
    // disable vertex attribute arrays
    glDisableVertexAttribArray(vertex_pos_location);
    glDisableVertexAttribArray(vertex_norm_location);
    if(not mesh->texcoord.empty()) glDisableVertexAttribArray(vertex_texcoord_location);
    if(mesh->skinning) {
        // YOUR CODE GOES HERE ---------------------
        // (only for extra credit)
        glDisableVertexAttribArray(vertex_skin_bone_ids_location);
        glDisableVertexAttribArray(vertex_skin_bone_weights_location);
    }
    
    // draw normals if needed
    if(draw_normals) {
        glUniform3fv(glGetUniformLocation(state->gl_program_id,"material_kd"),
                     1,&zero3f.x);
        glUniform3fv(glGetUniformLocation(state->gl_program_id,"material_ks"),
                     1,&zero3f.x);
        glBegin(GL_LINES);
        for(auto i : range(mesh->pos.size())) {
            auto p0 = mesh->pos[i];
            auto p1 = mesh->pos[i] + mesh->norm[i]*0.1;
            glVertexAttrib3fv(0,&p0.x);
            glVertexAttrib3fv(0,&p1.x);
            if(mesh->mat->double_sided) {
                auto p2 = mesh->pos[i] - mesh->norm[i]*0.1;
                glVertexAttrib3fv(0,&p0.x);
                glVertexAttrib3fv(0,&p2.x);
            }
        }
        glEnd();
    }
}
Exemple #3
0
// render the scene with OpenGL
void shade(Scene* scene, ShadeState* state) {
    // enable depth test
    glEnable(GL_DEPTH_TEST);
    glDepthFunc(GL_LEQUAL);

    // disable culling face
    glDisable(GL_CULL_FACE);

    // let the shader control the points
    glEnable(GL_POINT_SPRITE);
    
    // set up the viewport from the scene image size
    glViewport(0, 0, scene->image_width, scene->image_height);
    
    // clear the screen (both color and depth) - set cleared color to background
    glClearColor(scene->background.x, scene->background.y, scene->background.z, 1);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    
    // enable program
    glUseProgram(state->gl_program_id);
    
    // bind camera's position, inverse of frame and projection
    // use frame_to_matrix_inverse and frustum_matrix
    glUniform3fv(glGetUniformLocation(state->gl_program_id,"camera_pos"),
                 1, &scene->camera->frame.o.x);
    glUniformMatrix4fv(glGetUniformLocation(state->gl_program_id,"camera_frame_inverse"),
                       1, true, &frame_to_matrix_inverse(scene->camera->frame)[0][0]);
    glUniformMatrix4fv(glGetUniformLocation(state->gl_program_id,"camera_projection"),
                       1, true, &frustum_matrix(-scene->camera->dist*scene->camera->width/2, scene->camera->dist*scene->camera->width/2,
                                                -scene->camera->dist*scene->camera->height/2, scene->camera->dist*scene->camera->height/2,
                                                scene->camera->dist,10000)[0][0]);
    
    // bind ambient and number of lights
    glUniform3fv(glGetUniformLocation(state->gl_program_id,"ambient"),1,&scene->ambient.x);
    glUniform1i(glGetUniformLocation(state->gl_program_id,"lights_num"),scene->lights.size());
    
    // foreach light
    auto count = 0;
    for(auto light : scene->lights) {
        // bind light position and internsity (create param name with tostring)
        glUniform3fv(glGetUniformLocation(state->gl_program_id,tostring("light_pos[%d]",count).c_str()),
                     1, &light->frame.o.x);
        glUniform3fv(glGetUniformLocation(state->gl_program_id,tostring("light_intensity[%d]",count).c_str()),
                     1, &light->intensity.x);
        count++;
    }
    
    // foreach mesh
    for(auto mesh : scene->meshes) {
        // bind material kd, ks, n
        glUniform3fv(glGetUniformLocation(state->gl_program_id,"material_kd"),
                     1,&mesh->mat->kd.x);
        glUniform3fv(glGetUniformLocation(state->gl_program_id,"material_ks"),
                     1,&mesh->mat->ks.x);
        glUniform1f(glGetUniformLocation(state->gl_program_id,"material_n"),
                    mesh->mat->n);

        // YOUR CODE GOES HERE ---------------------
        // bind texture params (txt_on, sampler)
		_bind_texture("material_kd_txt", "material_kd_txt_on", mesh->mat->kd_txt, 0, state);
		_bind_texture("material_ks_txt", "material_ks_txt_on", mesh->mat->ks_txt, 1, state);
		_bind_texture("material_norm_txt", "material_norm_txt_on", mesh->mat->norm_txt, 2, state);

        // bind mesh frame - use frame_to_matrix
        glUniformMatrix4fv(glGetUniformLocation(state->gl_program_id,"mesh_frame"),
                           1,true,&frame_to_matrix(mesh->frame)[0][0]);
    
        // enable vertex attributes arrays and set up pointers to the mesh data
        auto vertex_pos_location = glGetAttribLocation(state->gl_program_id, "vertex_pos");
        auto vertex_norm_location = glGetAttribLocation(state->gl_program_id, "vertex_norm");

        // YOUR CODE GOES HERE ---------------------
		auto vertex_texcoord_location = glGetAttribLocation(state->gl_program_id, "vertex_texcoord");

        glEnableVertexAttribArray(vertex_pos_location);
        glVertexAttribPointer(vertex_pos_location, 3, GL_FLOAT, GL_FALSE, 0, &mesh->pos[0].x);
        glEnableVertexAttribArray(vertex_norm_location);
        glVertexAttribPointer(vertex_norm_location, 3, GL_FLOAT, GL_FALSE, 0, &mesh->norm[0].x);

		// YOUR CODE GOES HERE ---------------------
		if (!mesh->texcoord.empty())
		{

			glEnableVertexAttribArray(vertex_texcoord_location);
			glVertexAttribPointer(vertex_texcoord_location, 2, GL_FLOAT, GL_FALSE, 0, &mesh->texcoord[0].x);
		}
        
        // draw triangles and quads
        if(! scene->draw_wireframe) {
            if(mesh->triangle.size()) glDrawElements(GL_TRIANGLES, mesh->triangle.size()*3, GL_UNSIGNED_INT, &mesh->triangle[0].x);
            if(mesh->quad.size()) glDrawElements(GL_QUADS, mesh->quad.size()*4, GL_UNSIGNED_INT, &mesh->quad[0].x);
        } else {
            auto edges = EdgeMap(mesh->triangle, mesh->quad).edges();
            glDrawElements(GL_LINES, edges.size()*2, GL_UNSIGNED_INT, &edges[0].x);
        }
        
        // draw line sets
        if(! mesh->line.empty()) glDrawElements(GL_LINES, mesh->line.size()*2, GL_UNSIGNED_INT, mesh->line.data());
        for(auto segment : mesh->spline) glDrawElements(GL_LINE_STRIP, 4, GL_UNSIGNED_INT, &segment);
        
        // disable vertex attribute arrays
        glDisableVertexAttribArray(vertex_pos_location);
        glDisableVertexAttribArray(vertex_norm_location);

        // YOUR CODE GOES HERE ---------------------
		if (!mesh->texcoord.empty())
			glDisableVertexAttribArray(vertex_texcoord_location);
    }
}
Exemple #4
0
//----------------------------------------------------------------------------
CreateEnvelope::CreateEnvelope (int numVertices, const Vector2f* vertices,
                                int numIndices, const int* indices, int& numEnvelopeVertices,
                                Vector2f*& envelopeVertices)
{
	// The graph of vertices and edgeMaps to be used for constructing the
	// obstacle envelope.
	SegmentGraph* graph = new0 SegmentGraph();

	// Convert the vertices to rational points to allow exact arithmetic,
	// thereby avoiding problems with numerical round-off errors.
	RPoint2* ratVertices = new1<RPoint2>(numVertices);
	int i;
	for (i = 0; i < numVertices; ++i)
	{
		ratVertices[i].X() = RScalar(vertices[i].X());
		ratVertices[i].Y() = RScalar(vertices[i].Y());
	}

	// Insert the 2D mesh edgeMaps into the graph.
	const int* currentIndex = indices;
	int numTriangles = numIndices/3;
	for (i = 0; i < numTriangles; ++i)
	{
		int v0 = *currentIndex++;
		int v1 = *currentIndex++;
		int v2 = *currentIndex++;
		graph->InsertEdge(ratVertices[v0], ratVertices[v1]);
		graph->InsertEdge(ratVertices[v1], ratVertices[v2]);
		graph->InsertEdge(ratVertices[v2], ratVertices[v0]);
	}
	delete1(ratVertices);

	// Represent each edge as a map of points ordered by rational parameter
	// values, each point P(t) = End0 + t*(End1-End0), where End0 and End1
	// are the rational endpoints of the edge and t is the rational
	// parameter for the edge point P(t).
	std::set<SegmentGraph::Edge>& edgeSet = graph->GetEdges();
	int numEdges = (int)edgeSet.size();
	EdgeMap** edgeMaps = new1<EdgeMap*>(numEdges);
	std::set<SegmentGraph::Edge>::iterator esIter = edgeSet.begin();
	for (i = 0; i < numEdges; ++i, ++esIter)
	{
		SegmentGraph::Edge edge = *esIter;
		EdgeMap* edgeMap = new0 EdgeMap();
		(*edgeMap)[0] = edge.GetVertex(0)->Position;
		(*edgeMap)[1] = edge.GetVertex(1)->Position;
		edgeMaps[i] = edgeMap;
	}

	UpdateAllEdges(numEdges, edgeMaps);

	// Recreate the graph, now using the segmented edgeMaps from the original
	// graph.
	delete0(graph);
	graph = new0 SegmentGraph();
	for (i = 0; i < numEdges; ++i)
	{
		// Each graph edge is a pair of consecutive edge points.
		EdgeMap* edgeMap = edgeMaps[i];

		// Get first point.
		EdgeMap::iterator iter = edgeMap->begin();
		EdgeMap::iterator end = edgeMap->end();
		RPoint2* point0 = &iter->second;

		// Get remaining points.
		for (++iter; iter != end; ++iter)
		{
			RPoint2* point1 = &iter->second;
			graph->InsertEdge(*point0, *point1);
			point0 = point1;
		}

		delete0(edgeMap);
	}
	delete1(edgeMaps);

	std::vector<RPoint2> envelope;
	graph->ExtractEnvelope(envelope);

	// Convert the vertices back to floating-point values and return to the
	// caller.
	numEnvelopeVertices = (int)envelope.size();
	envelopeVertices = new1<Vector2f>(numEnvelopeVertices);
	for (i = 0; i < numEnvelopeVertices; ++i)
	{
		const RPoint2& point = envelope[i];
		point.X().ConvertTo(envelopeVertices[i].X());
		point.Y().ConvertTo(envelopeVertices[i].Y());
	}

	delete0(graph);
}