summaryrefslogtreecommitdiff
path: root/avcodec_audio_example1.c
blob: b296c003d846c6f3f7cf04b028a0a6a7d8d67af7 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
bool Render_context::load_audio(string &filename){
	//load audio into memory and create thumbnail
	AVCodec *codec;
	AVCodecContext *c= NULL;
	int len;
	FILE *f;
	uint8_t inbuf[AUDIO_INBUF_SIZE + FF_INPUT_BUFFER_PADDING_SIZE];
	AVPacket avpkt;
	AVFrame *decoded_frame = NULL;

	av_init_packet(&avpkt);

	// http://stackoverflow.com/questions/9799560/decode-audio-using-libavcodec-and-play-using-libao
	
	/* find the mpeg audio decoder */
	codec = avcodec_find_decoder(AV_CODEC_ID_MP2);
	if (!codec) {
		fprintf(stderr, "Codec not found\n");
		return false;
	}

	c = avcodec_alloc_context3(codec);
	if (!c) {
		fprintf(stderr, "Could not allocate audio codec context\n");
		return false;
	}

	/* open it */
	if (avcodec_open2(c, codec, NULL) < 0) {
		fprintf(stderr, "Could not open codec\n");
		return false;
	}

	f = fopen(filename.c_str(), "rb");
	if (!f) {
		fprintf(stderr, "Could not open %s\n", filename.c_str());
		return false;
	}

	/* decode until eof */
	avpkt.data = inbuf;
	avpkt.size = fread(inbuf, 1, AUDIO_INBUF_SIZE, f);

	while (avpkt.size > 0) {
		int got_frame = 0;

		if (!decoded_frame) {
			if (!(decoded_frame = avcodec_alloc_frame())) {
				printf("Could not allocate audio frame\n");
			return false;
			}
		} else
		avcodec_get_frame_defaults(decoded_frame);

		len = avcodec_decode_audio4(c, decoded_frame, &got_frame, &avpkt);
		if (len < 0) {
			fprintf(stderr, "Error while decoding\n");
			return false;
		}
		if (got_frame) {
			/* if a frame has been decoded, output it */
			int data_size = av_samples_get_buffer_size(NULL, c->channels,decoded_frame->nb_samples,c->sample_fmt, 1);
			//fwrite(decoded_frame->data[0], 1, data_size, outfile);
			
			//here is where we do something with the data
			//is it best to buffer it or do do all processing within a loop like this?
			
		}
		avpkt.size -= len;
		avpkt.data += len;
		avpkt.dts =
		avpkt.pts = AV_NOPTS_VALUE;
		if (avpkt.size < AUDIO_REFILL_THRESH) {
			/* Refill the input buffer, to avoid trying to decode
			* incomplete frames. Instead of this, one could also use
			* a parser, or use a proper container format through
			* libavformat. */
			memmove(inbuf, avpkt.data, avpkt.size);
			avpkt.data = inbuf;
			len = fread(avpkt.data + avpkt.size, 1,AUDIO_INBUF_SIZE - avpkt.size, f);
			if (len > 0)
			avpkt.size += len;
		}
	}

	fclose(f);

	avcodec_close(c);
	av_free(c);
	avcodec_free_frame(&decoded_frame);
    
	return true;
}