[Hello world 오픈 세미나]ffmpeg android

29
FFmpeg을 이용한 Android 동영상 플레이어 개발 NHN 동영상서비스개발2팀 김대웅 12526토요일

Transcript of [Hello world 오픈 세미나]ffmpeg android

Page 1: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한Android����������� ������������������  동영상����������� ������������������  플레이어����������� ������������������  개발

NHN동영상서비스개발2팀

김대웅

12년 5월 26일 토요일

Page 2: [Hello world 오픈 세미나]ffmpeg android

목차

Android에서의����������� ������������������  Multimedia

FFmpeg

FFmpeg����������� ������������������  &����������� ������������������  Android

FFmpeg을����������� ������������������  이용한����������� ������������������  Android����������� ������������������  동영상����������� ������������������  Player

Shader를����������� ������������������  사용한����������� ������������������  고성능(?)����������� ������������������  Player

마무리

12년 5월 26일 토요일

Page 3: [Hello world 오픈 세미나]ffmpeg android

Android에서의����������� ������������������  MultimediaAndroid

Mobile����������� ������������������  OS,����������� ������������������  Library,����������� ������������������  Application����������� ������������������  Framework����������� ������������������  등을����������� ������������������  포함하는����������� ������������������  Application����������� ������������������  Stack

Application����������� ������������������  개발은����������� ������������������  Java로,����������� ������������������  성능을����������� ������������������  요하는����������� ������������������  작업은����������� ������������������  native로

Android에서의����������� ������������������  Multimedia

대부분의����������� ������������������  작업은����������� ������������������  native에서����������� ������������������  이루어짐����������� ������������������  

Framework:����������� ������������������  OpenCore,����������� ������������������  Stagefright

12년 5월 26일 토요일

Page 4: [Hello world 오픈 세미나]ffmpeg android

Android에서의����������� ������������������  MultimediaCodec

순수����������� ������������������  Multimedia����������� ������������������  data는����������� ������������������  완전����������� ������������������  크다!����������� ������������������  압축이����������� ������������������  필요하다!

HOw?����������� ������������������  Codec을����������� ������������������  이용해서

Audio����������� ������������������  Codec:����������� ������������������  MP3,����������� ������������������  Vorbis,����������� ������������������  등

Video����������� ������������������  Codec:����������� ������������������  MPEG-4����������� ������������������  AVC(H.264),����������� ������������������  WMV9,����������� ������������������  등

12년 5월 26일 토요일

Page 5: [Hello world 오픈 세미나]ffmpeg android

Android에서의����������� ������������������  MultimediaContainer����������� ������������������  (Digital����������� ������������������  Container����������� ������������������  Format)

압축된����������� ������������������  Multimedia����������� ������������������  data

압축된����������� ������������������  data

meta����������� ������������������  data

구조화된����������� ������������������  저장����������� ������������������  방식이����������� ������������������  필요:����������� ������������������  .mp4,����������� ������������������  .wmv����������� ������������������  등

12년 5월 26일 토요일

Page 6: [Hello world 오픈 세미나]ffmpeg android

Android에서의����������� ������������������  Multimedia

실제����������� ������������������  File

원본����������� ������������������  Data압축된����������� ������������������  Data

Meta����������� ������������������  DataEncoding

Muxing

Demuxing

Decoding

12년 5월 26일 토요일

Page 7: [Hello world 오픈 세미나]ffmpeg android

FFmpegOpen����������� ������������������  Source����������� ������������������  Multimedia����������� ������������������  Framework

Cross-Platform

Encoding/Decoding,����������� ������������������  Muxing/Demuxing,����������� ������������������  Transcoding,����������� ������������������  등

libavcodec,����������� ������������������  libavformat,����������� ������������������  libavutil,����������� ������������������  libpostproc,����������� ������������������  libswscale,����������� ������������������  libavfilter,����������� ������������������  libswresample

12년 5월 26일 토요일

Page 8: [Hello world 오픈 세미나]ffmpeg android

FFmpegFFmpeg을����������� ������������������  이용한����������� ������������������  Multimedia����������� ������������������  재생

12년 5월 26일 토요일

Page 9: [Hello world 오픈 세미나]ffmpeg android

FFmpeg����������� ������������������  &����������� ������������������  AndroidFFmpeg은����������� ������������������  C로����������� ������������������  작성된����������� ������������������  코드

어떻게����������� ������������������  build하지?����������� ������������������  NDK����������� ������������������  (Native����������� ������������������  Development����������� ������������������  Kit)

Android����������� ������������������  Platform을����������� ������������������  이용하기����������� ������������������  위한����������� ������������������  header����������� ������������������  file,����������� ������������������  library

Native����������� ������������������  platform으로����������� ������������������  compile하기����������� ������������������  위한����������� ������������������  cross-tollchains

Android����������� ������������������  App.은����������� ������������������  Java로����������� ������������������  개발

어떻게����������� ������������������  FFmpeg하고����������� ������������������  연결하지?����������� ������������������  JNI����������� ������������������  (Java����������� ������������������  Native����������� ������������������  Interface)

12년 5월 26일 토요일

Page 10: [Hello world 오픈 세미나]ffmpeg android

FFmpeg����������� ������������������  &����������� ������������������  AndroidPlayer����������� ������������������  개발에는����������� ������������������  어떤����������� ������������������  기능����������� ������������������  들이����������� ������������������  더����������� ������������������  필요하지?

Data����������� ������������������  Queuing,����������� ������������������  Stream����������� ������������������  syncing,����������� ������������������  Rendering,����������� ������������������  등

뭘����������� ������������������  참고하지?����������� ������������������  ffplay

FFmpeg을����������� ������������������  이용하여����������� ������������������  Multimedia����������� ������������������  Player를����������� ������������������  구현해����������� ������������������  놓은����������� ������������������  일종의����������� ������������������  reference����������� ������������������  source

그럼����������� ������������������  끝?!����������� ������������������  NO

12년 5월 26일 토요일

Page 11: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한����������� ������������������  동영상����������� ������������������  Playerffplay를����������� ������������������  이용할����������� ������������������  때의����������� ������������������  문제점

C로����������� ������������������  작성된����������� ������������������  코드

rendering을����������� ������������������  위해����������� ������������������  SDL����������� ������������������  (Simple����������� ������������������  DirectMedia����������� ������������������  Layer)를����������� ������������������  사용

12년 5월 26일 토요일

Page 12: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한����������� ������������������  동영상����������� ������������������  PlayerAndroid의����������� ������������������  Audio����������� ������������������  Rendering

AudioTrack

12년 5월 26일 토요일

Page 13: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한����������� ������������������  동영상����������� ������������������  PlayerAndroid의����������� ������������������  Audio����������� ������������������  Rendering

AudioTrackpublic void startAudioDecoding(int sampleRate, int channels) {

int audioFormat = AudioFormat.ENCODING_PCM_16BIT;

int channelConfig = (channels > 1) ?

AudioFormat.CHANNEL_OUT_STEREO : AudioFormat.CHANNEL_OUT_MONO;

int bufferSize = AudioTrack.getMinBufferSize(sampleRate, channelConfig, audioFormat);

mAudioTrack = new AudioTrack(AudioManager.STREAM_MUSIC,

sampleRate, channelConfig, audioFormat, bufferSize,

AudioTrack.MODE_STREAM);

mBuffer = new byte[bufferSize];

mAudioThread = new Thread() {

@Override

public void run() {

nativeDecodeAudioStream();

Log.i(TAG, "[startAudioDecoding] done");

}

};

mAudioThread.start();

}

12년 5월 26일 토요일

Page 14: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한����������� ������������������  동영상����������� ������������������  PlayerAndroid의����������� ������������������  Audio����������� ������������������  Rendering

AudioTrackpublic void addAudioData(byte[] buffer) {

mAudioTrack.write(mBuffer, 0, buffer.length);

if (mAudioTrack.getPlayState() != AudioTrack.PLAYSTATE_PLAYING) {

mAudioTrack.play();

}

}

12년 5월 26일 토요일

Page 15: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한����������� ������������������  동영상����������� ������������������  PlayerAndroid의����������� ������������������  Video����������� ������������������  Rendering

GLSurfaceView

12년 5월 26일 토요일

Page 16: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한����������� ������������������  동영상����������� ������������������  PlayerAndroid의����������� ������������������  Video����������� ������������������  Rendering

GLSurfaceView// Decode a frame

avcodec_decode_video2(is->video_st->codec, frame, &got_picture, pkt);

// Render a frame

opengl_copyData(vp->picture.data, vp->picture.linesize[0], vp->width, vp->height);

// Convert color space (from YUV420 to RGB565)

sws_scale(is->img_convert_ctx, src_frame->data, src_frame->linesize, 0, vp->height,

pict.data, pict.linesize);

void opengl_copyData(void *data, int linesize, int width, int height) {

gFrameData[0] = ((uint8_t **)data)[0];

gFrameData[1] = ((uint8_t **)data)[1];

gFrameData[2] = ((uint8_t **)data)[2];

render();

}

12년 5월 26일 토요일

Page 17: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한����������� ������������������  동영상����������� ������������������  PlayerAndroid의����������� ������������������  Video����������� ������������������  Rendering

GLSurfaceView

12년 5월 26일 토요일

Page 18: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한����������� ������������������  동영상����������� ������������������  PlayerAndroid의����������� ������������������  Video����������� ������������������  Rendering

GLSurfaceViewstatic void bindTextures() {

glBindTexture(GL_TEXTURE_2D, gFrameTexture[0]);

glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, gFrameLinesize, gFrameHeight, GL_LUMINANCE,

GL_UNSIGNED_BYTE, gFrameData[0]);

glBindTexture(GL_TEXTURE_2D, gFrameTexture[1]);

glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, gFrameHalfLinesize, gFrameHalfHeight,

GL_LUMINANCE, GL_UNSIGNED_BYTE, gFrameData[1]);

glBindTexture(GL_TEXTURE_2D, gFrameTexture[2]);

glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, gFrameHalfLinesize, gFrameHalfHeight,

GL_LUMINANCE, GL_UNSIGNED_BYTE, gFrameData[2]);

}

12년 5월 26일 토요일

Page 19: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한����������� ������������������  동영상����������� ������������������  PlayerAndroid의����������� ������������������  Video����������� ������������������  Rendering

GLSurfaceView

12년 5월 26일 토요일

Page 20: [Hello world 오픈 세미나]ffmpeg android

FFmpeg을����������� ������������������  이용한����������� ������������������  동영상����������� ������������������  PlayerAndroid����������� ������������������  동영상����������� ������������������  Player

12년 5월 26일 토요일

Page 21: [Hello world 오픈 세미나]ffmpeg android

Shader를����������� ������������������  사용한����������� ������������������  고성능(?)����������� ������������������  Player색공간이����������� ������������������  뭐지??

pixel을����������� ������������������  이용해����������� ������������������  색을����������� ������������������  표현하는����������� ������������������  방식:����������� ������������������  YUV,����������� ������������������  RGB,����������� ������������������  YCbCr����������� ������������������  등

FFmpeg의����������� ������������������  결과����������� ������������������  물인����������� ������������������  pixel����������� ������������������  data는����������� ������������������  YUV,����������� ������������������  Android에서����������� ������������������  사용하는����������� ������������������  pixel����������� ������������������  data는����������� ������������������  RGB

변환을����������� ������������������  위해서는����������� ������������������  상당한����������� ������������������  시간이����������� ������������������  소요

예)����������� ������������������  1초����������� ������������������  영상,����������� ������������������  640����������� ������������������  x����������� ������������������  480����������� ������������������  x����������� ������������������  24����������� ������������������  =����������� ������������������  307,200����������� ������������������  x����������� ������������������  24����������� ������������������  =����������� ������������������  7,372,800

12년 5월 26일 토요일

Page 22: [Hello world 오픈 세미나]ffmpeg android

Shader를����������� ������������������  사용한����������� ������������������  고성능(?)����������� ������������������  PlayerFFmpeg을����������� ������������������  이용한����������� ������������������  색공간����������� ������������������  변환은����������� ������������������  어떻게?

libswscale:����������� ������������������  CPU만����������� ������������������  사용,����������� ������������������  너무����������� ������������������  느리다...

12년 5월 26일 토요일

Page 23: [Hello world 오픈 세미나]ffmpeg android

Shader를����������� ������������������  사용한����������� ������������������  고성능(?)����������� ������������������  Player더����������� ������������������  좋은����������� ������������������  방법은?����������� ������������������  Fragment����������� ������������������  Shader

GPU를����������� ������������������  이용해����������� ������������������  pixel의����������� ������������������  색상이나����������� ������������������  속성을����������� ������������������  변경,����������� ������������������  딱����������� ������������������  맞다!

12년 5월 26일 토요일

Page 24: [Hello world 오픈 세미나]ffmpeg android

Shader를����������� ������������������  사용한����������� ������������������  고성능(?)����������� ������������������  Player더����������� ������������������  좋은����������� ������������������  방법은?����������� ������������������  Fragment����������� ������������������  Shader

GPU를����������� ������������������  이용해����������� ������������������  pixel의����������� ������������������  색상이나����������� ������������������  속성을����������� ������������������  변경,����������� ������������������  딱����������� ������������������  맞다!

static const char fragmentShaderSource[] =

"uniform sampler2D sampler0;\n"

"uniform sampler2D sampler1;\n"

"uniform sampler2D sampler2;\n"

"varying highp vec2 _texcoord;\n"

"void main()\n"

"{\n"

"highp float y = texture2D(sampler0, _texcoord).r;\n"

"highp float u = texture2D(sampler1, _texcoord).r;\n"

"highp float v = texture2D(sampler2, _texcoord).r;\n"

"\n"

"y = 1.1643 * (y - 0.0625);\n"

"u = u - 0.5;\n"

"v = v - 0.5;\n"

"\n"

"highp float r = y + 1.5958 * v;\n"

"highp float g = y - 0.39173 * u - 0.81290 * v;\n"

"highp float b = y + 2.017 * u;\n"

"\n"

"gl_FragColor = vec4(r, g, b, 1.0);\n"

"}\n";

12년 5월 26일 토요일

Page 25: [Hello world 오픈 세미나]ffmpeg android

Shader를����������� ������������������  사용한����������� ������������������  고성능(?)����������� ������������������  Player더����������� ������������������  좋은����������� ������������������  방법은?����������� ������������������  Fragment����������� ������������������  Shader

GPU를����������� ������������������  이용해����������� ������������������  pixel의����������� ������������������  색상이나����������� ������������������  속성을����������� ������������������  변경,����������� ������������������  딱����������� ������������������  맞다!

12년 5월 26일 토요일

Page 26: [Hello world 오픈 세미나]ffmpeg android

Shader를����������� ������������������  사용한����������� ������������������  고성능(?)����������� ������������������  Player더����������� ������������������  좋은����������� ������������������  방법은?����������� ������������������  Fragment����������� ������������������  Shader

GPU를����������� ������������������  이용해����������� ������������������  pixel의����������� ������������������  색상이나����������� ������������������  속성을����������� ������������������  변경,����������� ������������������  딱����������� ������������������  맞다!static void setTexturesWithShader() {

//glEnable(GL_TEXTURE_2D);

glActiveTexture(GL_TEXTURE0);

glUniform1i(gShaderVariables.sampler0, 0);

glBindTexture(GL_TEXTURE_2D, gFrameTexture[0]);

glActiveTexture(GL_TEXTURE1);

glUniform1i(gShaderVariables.sampler1, 1);

glBindTexture(GL_TEXTURE_2D, gFrameTexture[1]);

glActiveTexture(GL_TEXTURE2);

glUniform1i(gShaderVariables.sampler2, 2);

glBindTexture(GL_TEXTURE_2D, gFrameTexture[2]);

}

12년 5월 26일 토요일

Page 27: [Hello world 오픈 세미나]ffmpeg android

Shader를����������� ������������������  사용한����������� ������������������  고성능(?)����������� ������������������  Player더����������� ������������������  좋은����������� ������������������  방법은?����������� ������������������  Fragment����������� ������������������  Shader

GPU를����������� ������������������  이용해����������� ������������������  pixel의����������� ������������������  색상이나����������� ������������������  속성을����������� ������������������  변경,����������� ������������������  딱����������� ������������������  맞다!

12년 5월 26일 토요일

Page 28: [Hello world 오픈 세미나]ffmpeg android

마무리Android는����������� ������������������  동영상����������� ������������������  잘����������� ������������������  돌아가는데����������� ������������������  왜����������� ������������������  이걸����������� ������������������  개발해야����������� ������������������  할까?

서비스의����������� ������������������  질����������� ������������������  (파편화)

FFmpeg을����������� ������������������  이용한����������� ������������������  다양한����������� ������������������  가능성

12년 5월 26일 토요일

Page 29: [Hello world 오픈 세미나]ffmpeg android

마무리Android는����������� ������������������  동영상����������� ������������������  잘����������� ������������������  돌아가는데����������� ������������������  왜����������� ������������������  이걸����������� ������������������  개발해야����������� ������������������  할까?

서비스의����������� ������������������  질����������� ������������������  (파편화)

FFmpeg을����������� ������������������  이용한����������� ������������������  다양한����������� ������������������  가능성

고맙습니다.12년 5월 26일 토요일