Exemplo n.º 1
0
void V4SceneManager::SaveFile(const char *path) 
{
	GF_SMEncodeOptions opts;
	char rad_name[5000];

	/* First dump the scene in a BT file */
	strcpy(rad_name, "dump");
	m_pSm->scene_graph->RootNode = NULL;
	gf_sm_dump(m_pSm, rad_name, 0);

	/* Then reload properly (overriding the current SceneManager)*/
	GF_SceneLoader load;
	memset(&load, 0, sizeof(GF_SceneLoader));
	load.fileName = "dump.bt";
	load.ctx = m_pSm;
	gf_sm_load_init(&load);
	gf_sm_load_run(&load);
	gf_sm_load_done(&load);

	/* Finally encode the file */
	GF_ISOFile *mp4 = gf_isom_open(path, GF_ISOM_WRITE_EDIT, NULL);
	m_pSm->max_node_id = gf_sg_get_max_node_id(m_pSm->scene_graph);
	memset(&opts, 0, sizeof(opts));
	opts.flags = GF_SM_LOAD_MPEG4_STRICT;
	gf_sm_encode_to_file(m_pSm, mp4, &opts);
	gf_isom_set_brand_info(mp4, GF_ISOM_BRAND_MP42, 1);
	gf_isom_modify_alternate_brand(mp4, GF_ISOM_BRAND_ISOM, 1);
	gf_isom_close(mp4);
}
Exemplo n.º 2
0
GF_Err encode_laser(GF_LoadCompare *lc, char *item_path, GF_ISOFile *mp4, GF_SMEncodeOptions *opts) 
{
	GF_Err e = GF_OK;
	GF_SceneLoader load;
	GF_SceneManager *ctx;
	GF_SceneGraph *sg;
	GF_StatManager *statsman = NULL;

	memset(&load, 0, sizeof(GF_SceneLoader));
	sg = gf_sg_new();
	ctx = gf_sm_new(sg);
	load.ctx = ctx;
	load.fileName = item_path;

	e = gf_sm_load_init(&load);
	if (e) {
		fprintf(stderr, "Error loading file %s\n", item_path);
	} else {
		e = gf_sm_load_run(&load);
		if (e) {
			fprintf(stderr, "Error loading file %s\n", item_path);
		} else {
			if (opts->auto_qant) {
				if (lc->verbose) fprintf(stdout, "Analysing Scene for Automatic Quantization\n");
				statsman = gf_sm_stats_new();
				e = gf_sm_stats_for_scene(statsman, ctx);
				if (!e) {
					GF_SceneStatistics *stats = gf_sm_stats_get(statsman);
					if (opts->resolution > (s32)stats->frac_res_2d) {
						if (lc->verbose) fprintf(stdout, " Given resolution %d is (unnecessarily) too high, using %d instead.\n", opts->resolution, stats->frac_res_2d);
						opts->resolution = stats->frac_res_2d;
					} else if (stats->int_res_2d + opts->resolution <= 0) {
						if (lc->verbose) fprintf(stdout, " Given resolution %d is too low, using %d instead.\n", opts->resolution, stats->int_res_2d - 1);
						opts->resolution = 1 - stats->int_res_2d;
					}				
					opts->coord_bits = stats->int_res_2d + opts->resolution;
					if (lc->verbose) fprintf(stdout, " Coordinates & Lengths encoded using ");
					if (opts->resolution < 0) {
						if (lc->verbose) fprintf(stdout, "only the %d most significant bits (of %d).\n", opts->coord_bits, stats->int_res_2d);
					} else {
						if (lc->verbose) fprintf(stdout, "a %d.%d representation\n", stats->int_res_2d, opts->resolution);
					}

					if (lc->verbose) fprintf(stdout, " Matrix Scale & Skew Coefficients ");
					if (opts->coord_bits < stats->scale_int_res_2d) {
						opts->scale_bits = stats->scale_int_res_2d - opts->coord_bits;
						if (lc->verbose) fprintf(stdout, "encoded using a %d.8 representation\n", stats->scale_int_res_2d);
					} else  {
						opts->scale_bits = 0;
						if (lc->verbose) fprintf(stdout, "not encoded.\n");
					}
				}
				gf_sm_stats_del(statsman);
			}
			
			e = gf_sm_encode_to_file(ctx, mp4, opts);
			if (e) {
				fprintf(stderr, "Error while encoding mp4 file\n");
			} else {
				e = gf_isom_set_brand_info(mp4, GF_ISOM_BRAND_MP42, 1);
				if (!e) e = gf_isom_modify_alternate_brand(mp4, GF_ISOM_BRAND_ISOM, 1);
			}

			gf_sm_load_done(&load);
		}		
	}
	gf_sm_del(ctx);
	gf_sg_del(sg);

	return e;
}
Exemplo n.º 3
0
GF_Err adobize_segment(GF_ISOFile *isom_file, AdobeHDSCtx *ctx)
{
	GF_Err e;
	GF_BitStream *bs;

	GF_AdobeFragRandomAccessBox *afra = (GF_AdobeFragRandomAccessBox*)	afra_New();
	GF_AfraEntry *ae                  = (GF_AfraEntry*)					gf_calloc(1, sizeof(GF_AfraEntry));
	GF_AdobeBootstrapInfoBox *abst    = (GF_AdobeBootstrapInfoBox*)		abst_New();
	GF_AdobeSegmentRunTableBox *asrt  = (GF_AdobeSegmentRunTableBox*)	asrt_New();
	GF_AdobeSegmentRunEntry *asre     = (GF_AdobeSegmentRunEntry*)		gf_calloc(1, sizeof(GF_AdobeSegmentRunEntry));
	GF_AdobeFragmentRunTableBox *afrt = (GF_AdobeFragmentRunTableBox*)	afrt_New();
	GF_AdobeFragmentRunEntry *afre    = (GF_AdobeFragmentRunEntry*)		gf_calloc(1, sizeof(GF_AdobeFragmentRunEntry));

	u64 init_seg_time = ctx->curr_time;
	u32 seg_duration = (u32)gf_isom_get_duration(isom_file);

	//update context
	ctx->curr_time += seg_duration;

	//Adobe specific boxes
	//Random Access
	afra->type = GF_4CC('a', 'f', 'r', 'a');
	afra->version = 0;
	afra->flags = 0;
	afra->long_ids = 1;
	afra->long_offsets = 1;
	afra->global_entries = 0;
	afra->time_scale = gf_isom_get_timescale(isom_file);

	afra->entry_count = 1;
	ae->time = init_seg_time;
	ae->offset = 3999;
	gf_list_add(afra->local_access_entries, ae);

	afra->global_entries = 0;
	afra->global_entry_count = 0;

	e = gf_list_add(isom_file->TopBoxes, afra);
	if (e) {
		fprintf(stderr, "Impossible to write AFRA box: %s\n", gf_error_to_string(e));
		assert(0);
		return e;
	}

	//Bootstrap Info
	abst->type = GF_4CC('a', 'b', 's', 't');
	abst->version = 0;
	abst->flags = 0;
	abst->bootstrapinfo_version = 1;
	abst->profile = 0;
	abst->live = 1;
	abst->update = 0;
	abst->time_scale = gf_isom_get_timescale(isom_file);
	abst->current_media_time = init_seg_time+seg_duration;
	abst->smpte_time_code_offset = 0;

	abst->movie_identifier = NULL;
	abst->drm_data = NULL;
	abst->meta_data = NULL;

	abst->server_entry_count = 0;
	abst->quality_entry_count = 0;

	abst->segment_run_table_count = 1;
	{
		//Segment Run
		asrt->type = GF_4CC('a', 's', 'r', 't');
		asrt->version = 0;
		asrt->flags = 0;
		asrt->segment_run_entry_count = 1;
		{
			asre->first_segment = ctx->segnum;
			asre->fragment_per_segment = 1;
		}
		e = gf_list_add(asrt->segment_run_entry_table, asre);
		if (e) {
			fprintf(stderr, "Impossible to write ASR Entry: %s\n", gf_error_to_string(e));
			assert(0);
			return e;
		}
	}
	e = gf_list_add(abst->segment_run_table_entries, asrt);
	if (e) {
		fprintf(stderr, "Impossible to write ASRT box: %s\n", gf_error_to_string(e));
		assert(0);
		return e;
	}

	abst->fragment_run_table_count = 1;
	{
		//Fragment Run
		afrt->type = GF_4CC('a', 'f', 'r', 't');
		afrt->version = 0;
		afrt->flags = 0;
		afrt->timescale = gf_isom_get_timescale(isom_file);
		afrt->fragment_run_entry_count = 1;
		{
			afre->first_fragment = 1;
			afre->first_fragment_timestamp = 0;
			afre->fragment_duration = seg_duration;
		}
		e = gf_list_add(afrt->fragment_run_entry_table, afre);
		if (e) {
			fprintf(stderr, "Impossible to write AFR Entry: %s\n", gf_error_to_string(e));
			assert(0);
			return e;
		}
	}
	e = gf_list_add(abst->fragment_run_table_entries, afrt);
	if (e) {
		fprintf(stderr, "Impossible to write AFRT box: %s\n", gf_error_to_string(e));
		assert(0);
		return e;
	}

	e = gf_list_add(isom_file->TopBoxes, abst);
	if (e) {
		fprintf(stderr, "Impossible to write ABST box: %s\n", gf_error_to_string(e));
		assert(0);
		return e;
	}

	e = abst_Size((GF_Box*)abst);
	if (e) {
		fprintf(stderr, "Impossible to compute ABST box size: %s\n", gf_error_to_string(e));
		assert(0);
		return e;
	}
	ctx->bootstrap_size = (size_t)abst->size;
	ctx->bootstrap = gf_malloc(ctx->bootstrap_size);
	bs = gf_bs_new(ctx->bootstrap, ctx->bootstrap_size, GF_BITSTREAM_WRITE);
	e = abst_Write((GF_Box*)abst, bs);
	if (e) {
		fprintf(stderr, "Impossible to code the ABST box: %s\n", gf_error_to_string(e));
		assert(0);
		gf_bs_del(bs);
		return e;
	}
	gf_bs_del(bs);

	//set brands as reversed engineered from f4v files
	/*e = gf_isom_reset_alt_brands(isom_file);
	if (e) {
		fprintf(stderr, "Warning: couldn't reset ISOM brands: %s\n", gf_error_to_string(e));
		assert(0);
	}*/
	gf_isom_set_brand_info(isom_file, GF_4CC('f','4','v',' '), 1);
	gf_isom_modify_alternate_brand(isom_file, GF_4CC('i','s','o','m'), 1);
	gf_isom_modify_alternate_brand(isom_file, GF_4CC('m','p','4','2'), 1);
	gf_isom_modify_alternate_brand(isom_file, GF_4CC('m','4','v',' '), 1);

	return GF_OK;
}