예제 #1
0
/** This function should be called whenever a mouse cursor motion
 * occurs and is automatically called by
 * mousemove_glfwCursorPosCallback() and mousemove_glutMotionFunc()
 *
 * @param x The x coordinate of the mouse cursor.
 * @param y The y coordinate of the mouse cursor.
 * @return 1 if the scene needs to be redawn, 0 otherwise.
 */
int mousemove_movement(int x, int y)
{
	if(cur_button == -1)
		return 0;

	/* Distance cursor has moved since last press. */
	int dx = x-last_x;
	int dy = y-last_y;
	/* Vectors to store our orthonormal basis. */
	float f[3], r[3], u[3];

	// Calculate a new vector pointing from the camera to the
	// look at point and normalize it.
	vec3f_sub_new(f,cam_lookat_down,cam_position_down);
	vec3f_normalize(f);

	// Get our up vector
	vec3f_copy(u,cam_up);

	// Get a right vector based on the up and lookat vector.
	vec3f_cross_new(r, f, u);

	// If right vector was short, then look vector was pointing in
	// nearly the same direction as the up vector.
	if(vec3f_normSq(r) < EPSILON)
	{
		//printf("mousemove: whoops, pointed camera at up vector.");
		// move the up vector slightly and try again:
		u[0] += 0.05;
		vec3f_cross_new(r,f,u);
	}
	vec3f_normalize(r);

	// recalculate the up vector from the right vector and up vector
	// to ensure we have a an orthonormal basis.
	vec3f_cross_new(u, r, f);
	vec3f_normalize(u);

	switch(cur_button)
	{
		case 0: // left mouse button - translate left/right or up/down

			/* Translate the camera along the right and up vectors
			 * appropriately depending on the type of mouse movement.  */
			for(int i=0; i<3; i++)
			{
				float offset = r[i]*dx*settings_trans_scale + -u[i]*dy*settings_trans_scale;
				cam_position[i] = cam_position_down[i] - offset;
				cam_lookat[i]   = cam_lookat_down[i]   - offset;
			}
			break;

		case 1: // middle mouse button - translate forward and back
			mousemove_translate_inout(dy, f);
			break;

		case 2: // right mouse button - rotate

			// If the mouse is moved left/right, rotate the facing
			// vector around the up vector.
			mousemove_private_rotate_point(dx*settings_rot_scale, u, f);
			// If the mouse is moved up/down, rotate the facing vector
			// around the right vector.
			mousemove_private_rotate_point(dy*settings_rot_scale, r, f);
			vec3f_normalize(f);

			// Add new facing vector to the position that the camera
			// was at when the button was first pressed to get a new
			// lookat point.
			vec3f_add_new(cam_lookat, cam_position_down, f);
			break;
	}

	return 1;
}
예제 #2
0
/** Creates a cylinder geometry object. */
void init_geometryCylinder(kuhl_geometry *cyl, GLuint prog)
{
	int numSides=50;
	
	GLfloat vertices[1024];
	GLfloat normals[1024];
	GLuint indices[1024];
	GLfloat texcoords[1024];
	int verticesIndex = 0;
	int normalsIndex = 0;
	int indicesIndex = 0;
	int texcoordsIndex = 0;

	// Bottom middle
	vertices[verticesIndex++] = 0;
	vertices[verticesIndex++] = -.5;
	vertices[verticesIndex++] = -0;
	normals[normalsIndex++] = 0;
	normals[normalsIndex++] = -1;
	normals[normalsIndex++] = 0;
	texcoords[texcoordsIndex++] = 0;
	texcoords[texcoordsIndex++] = 0;
	

	// For each vertex around bottom perimeter
	for(int i=0; i<numSides; i++)
	{
		vertices[verticesIndex++] = .5*sin(i*2*M_PI/numSides);
		vertices[verticesIndex++] = -.5;
		vertices[verticesIndex++] = .5*cos(i*2*M_PI/numSides);
		normals[normalsIndex++] = 0;
		normals[normalsIndex++] = -1;
		normals[normalsIndex++] = 0;
		texcoords[texcoordsIndex++] = 0;
		texcoords[texcoordsIndex++] = 0;
	}

	// For each face/triangle on bottom, what are the 3 vertices?
	for(int i=0; i<numSides; i++)
	{
		indices[indicesIndex++] = 0;    // center point
		indices[indicesIndex++] = i+1;
		if(i+2 >= numSides+1)
			indices[indicesIndex++] = 1;
		else
			indices[indicesIndex++] = i+2;
	}


	int verticesIndexTopStart = verticesIndex;
	// Bottom middle
	vertices[verticesIndex++] = 0;
	vertices[verticesIndex++] = .5;
	vertices[verticesIndex++] = -0;
	normals[normalsIndex++] = 0;
	normals[normalsIndex++] = 1;
	normals[normalsIndex++] = 0;
	texcoords[texcoordsIndex++] = 1;
	texcoords[texcoordsIndex++] = 1;


	// For each vertex around bottom perimeter
	for(int i=0; i<numSides; i++)
	{
		vertices[verticesIndex++] = .5*sin(i*2*M_PI/numSides);
		vertices[verticesIndex++] = .5;
		vertices[verticesIndex++] = .5*cos(i*2*M_PI/numSides);
		normals[normalsIndex++] = 0;
		normals[normalsIndex++] = 1;
		normals[normalsIndex++] = 0;
		texcoords[texcoordsIndex++] = 1;
		texcoords[texcoordsIndex++] = 1;
	}

	// For each face/triangle on bottom
	for(int i=0; i<numSides; i++)
	{
		indices[indicesIndex++] = verticesIndexTopStart/3;    // center point
		indices[indicesIndex++] = verticesIndexTopStart/3+i+1;
		if(i+2 >= numSides+1)
			indices[indicesIndex++] = verticesIndexTopStart/3+1;
		else
			indices[indicesIndex++] = verticesIndexTopStart/3+i+2;
	}

	// For each vertex on faces on the sides of the cylinder
	for(int i=0; i<numSides; i++)
	{
		vertices[verticesIndex++] = .5*sin(i*2*M_PI/numSides);
		vertices[verticesIndex++] = .5;
		vertices[verticesIndex++] = .5*cos(i*2*M_PI/numSides);

		vertices[verticesIndex++] = .5*sin(i*2*M_PI/numSides);
		vertices[verticesIndex++] = -.5;
		vertices[verticesIndex++] = .5*cos(i*2*M_PI/numSides);

		vertices[verticesIndex++] = .5*sin((i+1)*2*M_PI/numSides);
		vertices[verticesIndex++] = -.5;
		vertices[verticesIndex++] = .5*cos((i+1)*2*M_PI/numSides);

		vertices[verticesIndex++] = .5*sin((i+1)*2*M_PI/numSides);
		vertices[verticesIndex++] = .5;
		vertices[verticesIndex++] = .5*cos((i+1)*2*M_PI/numSides);

		for(int j=0; j<4; j++)
		{
			float pt1[] = { vertices[verticesIndex-3*4+0],
			                vertices[verticesIndex-3*4+1],
			                vertices[verticesIndex-3*4+2] };
			float pt2[] = { vertices[verticesIndex-3*4+3],
			                vertices[verticesIndex-3*4+4],
			                vertices[verticesIndex-3*4+5] };
			float pt3[] = { vertices[verticesIndex-3*4+6],
			                vertices[verticesIndex-3*4+7],
			                vertices[verticesIndex-3*4+8] };
			float v1[3],v2[3],n[3];
			vec3f_sub_new(v1, pt2,pt1);
			vec3f_sub_new(v2, pt3,pt1);
			vec3f_cross_new(n, v1, v2);

			normals[normalsIndex++] = n[0];
			normals[normalsIndex++] = n[1];
			normals[normalsIndex++] = n[2];

			if(j < 2)
				texcoords[texcoordsIndex++] = (numSides-i)/(float)numSides;
			else
				texcoords[texcoordsIndex++] = (numSides-(i+1))/(float)numSides;

			if(j == 1 || j == 2)
				texcoords[texcoordsIndex++] = 0; // bottom
			else
				texcoords[texcoordsIndex++] = 1; // top
		}

		indices[indicesIndex++] = verticesIndex/3-4;
		indices[indicesIndex++] = verticesIndex/3-3;
		indices[indicesIndex++] = verticesIndex/3-2;

		indices[indicesIndex++] = verticesIndex/3-4;
		indices[indicesIndex++] = verticesIndex/3-2;
		indices[indicesIndex++] = verticesIndex/3-1;
	}

	kuhl_geometry_new(cyl, prog, verticesIndex/3, GL_TRIANGLES);
	kuhl_geometry_attrib(cyl, vertices, 3, "in_Position", 1);
	kuhl_geometry_attrib(cyl, normals, 3, "in_Normal", 1);
	kuhl_geometry_attrib(cyl, texcoords, 2, "in_TexCoord", 1);
	kuhl_geometry_indices(cyl, indices, indicesIndex);

	/*
	  printf("v: %d\n", verticesIndex);
	  printf("n: %d\n", normalsIndex);
	  printf("t: %d\n", texcoordsIndex);
	  printf("i: %d\n", indicesIndex);
	*/
}