示例#1
0
static void tsmf_presentation_restore_last_video_frame(TSMF_PRESENTATION* presentation)
{
	RDP_REDRAW_EVENT* revent;

	if (presentation->last_width && presentation->last_height)
	{
		revent = (RDP_REDRAW_EVENT*) freerdp_event_new(TsmfChannel_Class, TsmfChannel_Redraw,
			NULL, NULL);

		revent->x = presentation->last_x;
		revent->y = presentation->last_y;
		revent->width = presentation->last_width;
		revent->height = presentation->last_height;

		if (!tsmf_push_event(presentation->channel_callback, (wMessage*) revent))
		{
			freerdp_event_free((wMessage*) revent);
		}

		presentation->last_x = 0;
		presentation->last_y = 0;
		presentation->last_width = 0;
		presentation->last_height = 0;
	}
}
示例#2
0
static void tsmf_presentation_restore_last_video_frame(TSMF_PRESENTATION* presentation)
{
	RDP_REDRAW_EVENT* revent;

	if (presentation->last_width && presentation->last_height)
	{
		revent = (RDP_REDRAW_EVENT*) freerdp_event_new(RDP_EVENT_CLASS_TSMF, RDP_EVENT_TYPE_TSMF_REDRAW,
			NULL, NULL);
		revent->x = presentation->last_x;
		revent->y = presentation->last_y;
		revent->width = presentation->last_width;
		revent->height = presentation->last_height;
		if (!tsmf_push_event(presentation->channel_callback, (RDP_EVENT*) revent))
		{
			freerdp_event_free((RDP_EVENT*) revent);
		}
		presentation->last_x = 0;
		presentation->last_y = 0;
		presentation->last_width = 0;
		presentation->last_height = 0;
	}
}
示例#3
0
static void tsmf_sample_playback_video(TSMF_SAMPLE* sample)
{
	UINT64 t;
	RDP_VIDEO_FRAME_EVENT* vevent;
	TSMF_STREAM* stream = sample->stream;
	TSMF_PRESENTATION* presentation = stream->presentation;

	DEBUG_DVC("MessageId %d EndTime %d data_size %d consumed.",
		sample->sample_id, (int)sample->end_time, sample->data_size);

	if (sample->data)
	{
		t = get_current_time();

		if (stream->next_start_time > t &&
			(sample->end_time >= presentation->audio_start_time ||
			sample->end_time < stream->last_end_time))
		{
			USleep((stream->next_start_time - t) / 10);
		}
		stream->next_start_time = t + sample->duration - 50000;

		if (presentation->last_x != presentation->output_x ||
			presentation->last_y != presentation->output_y ||
			presentation->last_width != presentation->output_width ||
			presentation->last_height != presentation->output_height ||
			presentation->last_num_rects != presentation->output_num_rects ||
			(presentation->last_rects && presentation->output_rects &&
			memcmp(presentation->last_rects, presentation->output_rects,
			presentation->last_num_rects * sizeof(RDP_RECT)) != 0))
		{
			tsmf_presentation_restore_last_video_frame(presentation);

			presentation->last_x = presentation->output_x;
			presentation->last_y = presentation->output_y;
			presentation->last_width = presentation->output_width;
			presentation->last_height = presentation->output_height;

			if (presentation->last_rects)
			{
				free(presentation->last_rects);
				presentation->last_rects = NULL;
			}

			presentation->last_num_rects = presentation->output_num_rects;

			if (presentation->last_num_rects > 0)
			{
				presentation->last_rects = malloc(presentation->last_num_rects * sizeof(RDP_RECT));
				ZeroMemory(presentation->last_rects, presentation->last_num_rects * sizeof(RDP_RECT));

				memcpy(presentation->last_rects, presentation->output_rects,
					presentation->last_num_rects * sizeof(RDP_RECT));
			}
		}

		vevent = (RDP_VIDEO_FRAME_EVENT*) freerdp_event_new(TsmfChannel_Class, TsmfChannel_VideoFrame,
			NULL, NULL);

		vevent->frame_data = sample->data;
		vevent->frame_size = sample->decoded_size;
		vevent->frame_pixfmt = sample->pixfmt;
		vevent->frame_width = sample->stream->width;
		vevent->frame_height = sample->stream->height;
		vevent->x = presentation->output_x;
		vevent->y = presentation->output_y;
		vevent->width = presentation->output_width;
		vevent->height = presentation->output_height;

		if (presentation->output_num_rects > 0)
		{
			vevent->num_visible_rects = presentation->output_num_rects;

			vevent->visible_rects = (RDP_RECT*) malloc(presentation->output_num_rects * sizeof(RDP_RECT));
			ZeroMemory(vevent->visible_rects, presentation->output_num_rects * sizeof(RDP_RECT));

			memcpy(vevent->visible_rects, presentation->output_rects,
				presentation->output_num_rects * sizeof(RDP_RECT));
		}

		/* The frame data ownership is passed to the event object, and is freed after the event is processed. */
		sample->data = NULL;
		sample->decoded_size = 0;

		if (!tsmf_push_event(sample->channel_callback, (wMessage*) vevent))
		{
			freerdp_event_free((wMessage*) vevent);
		}

#if 0
		/* Dump a .ppm image for every 30 frames. Assuming the frame is in YUV format, we
		   extract the Y values to create a grayscale image. */
		static int frame_id = 0;
		char buf[100];
		FILE * fp;
		if ((frame_id % 30) == 0)
		{
			snprintf(buf, sizeof(buf), "/tmp/FreeRDP_Frame_%d.ppm", frame_id);
			fp = fopen(buf, "wb");
			fwrite("P5\n", 1, 3, fp);
			snprintf(buf, sizeof(buf), "%d %d\n", sample->stream->width, sample->stream->height);
			fwrite(buf, 1, strlen(buf), fp);
			fwrite("255\n", 1, 4, fp);
			fwrite(sample->data, 1, sample->stream->width * sample->stream->height, fp);
			fflush(fp);
			fclose(fp);
		}
		frame_id++;
#endif
	}
}