Beispiel #1
0
static void camOrbit(int dx, int dy)
{
	const double radius = 200;
	double dist;
	Vec3 v = cam_position;
	Quaternion o = cam_orientation;
	Quaternion q, q2;

	/* We invert the transformation because we are transforming the camera
	 * and not the scene. */
	q = quat_conjugate(quat_trackball(dx, dy, radius));

	/* The quaternion q gives us an intrinsic transformation, close to unity.
	 * To make it extrinsic, we compute q2 = o * q * ~o */
	q2 = quat_multiply(o, quat_multiply(q, quat_conjugate(o)));
	q2 = quat_normalize(q2);

	/* As round-off errors accumulate, the distance between the camera and the
	 * target would normally fluctuate. We take steps to prevent that here. */
	dist = vec3_length(v);
	v = quat_transform(q2, v);
	v = vec3_normalize(v);
	v = vec3_scale(v, dist);

	cam_position = v;
	cam_orientation = quat_multiply(q2, cam_orientation);
}
Beispiel #2
0
Vec3 kepler_position_at_E(KeplerOrbit *orbit, double E)
{
    double e = orbit->Ecc;
    double a = orbit->SMa, b = a * sqrt(1 - e*e);
    Vec3 plane_pos;

    plane_pos.x = a * (cos(E) - e);
    plane_pos.y = b * sin(E);
    plane_pos.z = 0;

    return quat_transform(orbit->plane_orientation, plane_pos);
}
Beispiel #3
0
Vec3 kepler_position_at_true_anomaly(KeplerOrbit *orbit, double theta)
{
    double e = orbit->Ecc;
    double p = orbit->SMa * (1-e*e);
    Vec3 plane_pos;

    plane_pos.x = p / (1 + e*cos(theta)) * cos(theta);
    plane_pos.y = p / (1 + e*cos(theta)) * sin(theta);
    plane_pos.z = 0;

    return quat_transform(orbit->plane_orientation, plane_pos);
}
Beispiel #4
0
bool handle_input(ALLEGRO_EVENT_QUEUE *ev_queue, Camera *cam)
{
	ALLEGRO_EVENT ev;
	ALLEGRO_MOUSE_STATE state;

	while (al_get_next_event(ev_queue, &ev))
	{
		switch (ev.type)
		{
		case ALLEGRO_EVENT_DISPLAY_CLOSE:
			return false;
			break;
		case ALLEGRO_EVENT_MOUSE_BUTTON_UP:
			//al_show_mouse_cursor(dpy);
			//al_ungrab_mouse();
			break;
		case ALLEGRO_EVENT_MOUSE_BUTTON_DOWN:
			//al_hide_mouse_cursor(dpy);
			//al_grab_mouse(dpy);
			break;
		case ALLEGRO_EVENT_MOUSE_AXES:
			if (ev.mouse.dz != 0)
				cam_dolly(cam, ev.mouse.dz);
			al_get_mouse_state(&state);

			/* The y coordinate needs to be inverted because OpenGL has
			 * the origin in the lower-left and Allegro the upper-left */
			if (state.buttons & 1)
				cam_orbit(cam, ev.mouse.dx, -ev.mouse.dy);
			else if (state.buttons & 2)
				cam_rotate(cam, ev.mouse.dx, -ev.mouse.dy);
			break;
		case ALLEGRO_EVENT_KEY_CHAR:
			if (ev.keyboard.unichar == 'w')
			{
				wireframe = !wireframe;
				if (wireframe)
				{
					glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
					glDisable(GL_CULL_FACE);
				}
				else
				{
					glPolygonMode(GL_FRONT, GL_FILL);
					glEnable(GL_CULL_FACE);
				}
			} else if (ev.keyboard.unichar == 'c')
			{
				Vec3 upv = quat_transform(cam->orientation, (Vec3){0, 1, 0});
				cam_lookat(cam, cam->position, cam->target, upv);
			}
			break;
		case ALLEGRO_EVENT_DISPLAY_RESIZE:
			cam->width = ev.display.width;
			cam->height = ev.display.height;
			glmLoadIdentity(glmProjectionMatrix);
			cam_projection_matrix(cam, glmProjectionMatrix);
			glViewport(cam->left, cam->bottom, cam->width, cam->height);
		default:
			break;
		}
	}

	return true;
}