{"action":"created","issue":{"url":"https://api.github.com/repos/bytedeco/javacv/issues/224","labels_url":"https://api.github.com/repos/bytedeco/javacv/issues/224/labels{/name}","comments_url":"https://api.github.com/repos/bytedeco/javacv/issues/224/comments","events_url":"https://api.github.com/repos/bytedeco/javacv/issues/224/events","html_url":"https://github.com/bytedeco/javacv/issues/224","id":107144002,"number":224,"title":"Image Dislocation problem encountered using javacv when recording on android,please help.","user":{"login":"ProgrammerYuan","id":5723923,"avatar_url":"https://avatars.githubusercontent.com/u/5723923?v=3","gravatar_id":"","url":"https://api.github.com/users/ProgrammerYuan","html_url":"https://github.com/ProgrammerYuan","followers_url":"https://api.github.com/users/ProgrammerYuan/followers","following_url":"https://api.github.com/users/ProgrammerYuan/following{/other_user}","gists_url":"https://api.github.com/users/ProgrammerYuan/gists{/gist_id}","starred_url":"https://api.github.com/users/ProgrammerYuan/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/ProgrammerYuan/subscriptions","organizations_url":"https://api.github.com/users/ProgrammerYuan/orgs","repos_url":"https://api.github.com/users/ProgrammerYuan/repos","events_url":"https://api.github.com/users/ProgrammerYuan/events{/privacy}","received_events_url":"https://api.github.com/users/ProgrammerYuan/received_events","type":"User","site_admin":false},"labels":[],"state":"open","locked":false,"assignee":null,"milestone":null,"comments":1,"created_at":"2015-09-18T06:47:44Z","updated_at":"2015-09-18T08:18:47Z","closed_at":null,"body":"Hello,Samuel:\r\n\tFirst,really thank you for developing such a brilliant project.After wrestling with original ffmpeg for months,JavaCV just like a GodSend to me. \r\n\tHere’s the problem, I 'm developing a simple app which enable every one to record and share their shining life moment with others in least steps. I integrated JavaCV Library(including ffmpeg 2.6) in my project.But when I play the video recorded, i find that in the video, a strip of frame which should appear on the right of the screen appears on the left side,if you don't understand what i just say, please see the image follow.\r\n![ffmpeg_example](https://cloud.githubusercontent.com/assets/5723923/9953479/cbaab4f4-5e13-11e5-9daf-e4cd1a775012.jpg)\r\n\r\n\r\nThe image above is a part of a frame extracted from the video, forgive me for cropping it because my friend don't like to be famous,LOL.But I believe you can get my point with it.\r\nAlso i rotate the video orientation and record again, but the disloaction still appears on the left.SO I'm thinking this is because I'm not using ffmpeg right.\r\nPlease help me...\r\n\r\nand the option I set as below:\r\nvideo_format:mp4\r\nvideo_size:864 * 480\r\nvideo_codec:H264\r\nvideo_bitrate:900k\r\nframe_rate:18\r\n\r\nHere's my code:\r\npublic class JavaCVRecordeActivity extends Activity implements OnClickListener, SurfaceHolder.Callback, PreviewCallback {\r\n\r\n\tprivate final static String CLASS_LABEL = \"RecordActivity\";\r\n\tprivate final static String LOG_TAG = CLASS_LABEL;\r\n\r\n\tprivate PowerManager.WakeLock mWakeLock;\r\n\r\n\tprivate String ffmpeg_link = \"/mnt/sdcard/stream.mp4\";\r\n\r\n\tlong startTime = 0;\r\n\tboolean recording = false;\r\n\r\n\tprivate FFmpegFrameRecorder recorder;\r\n\r\n\tprivate int sampleAudioRateInHz = 44100;\r\n\tprivate int imageWidth = 320;\r\n\tprivate int imageHeight = 240;\r\n\tprivate int frameRate = 20;\r\n\r\n\t/* audio data getting thread */\r\n\tprivate AudioRecord audioRecord;\r\n\tprivate AudioRecordRunnable audioRecordRunnable;\r\n\tprivate Thread audioThread;\r\n\tvolatile boolean runAudioThread = true;\r\n\r\n\t/* video data getting thread */\r\n\tprivate Camera cameraDevice;\r\n\tprivate Frame yuvImage = null;\r\n\tprivate Button btnRecorderControl, btnEffectChange, btnSnap;\r\n\r\n\tList<String> effects = new ArrayList<>();\r\n\tint index = 0;\r\n\t/* The number of seconds in the continuous record loop (or 0 to disable loop). */\r\n\tfinal int RECORD_LENGTH = 10;\r\n\tprivate final int ARRAY_LENGTH = RECORD_LENGTH * frameRate;\r\n\tprivate final int roller_length = 3 * frameRate;\r\n\tYuvImage image;\r\n\tArrayList<Frame> images;\r\n\tint operate_index = 0;\r\n\tArrayList<Long> timestamps;\r\n\tShortBuffer[] samples;\r\n\tint imagesIndex, samplesIndex;\r\n\tSurfaceView surfaceView;\r\n\tprivate boolean toSnap = false;\r\n\r\n\t@Override\r\n\tpublic void onCreate(Bundle savedInstanceState) {\r\n\t\tsuper.onCreate(savedInstanceState);\r\n\t\tsetContentView(R.layout.javacv_main);\r\n\t\tinitLayout();\r\n\t}\r\n\r\n\r\n\t@Override\r\n\tprotected void onResume() {\r\n\t\tsuper.onResume();\r\n\t}\r\n\r\n\t@Override\r\n\tprotected void onPause() {\r\n\t\tsuper.onPause();\r\n\t}\r\n\r\n\t@Override\r\n\tprotected void onDestroy() {\r\n\t\tsuper.onDestroy();\r\n\r\n\t\trecording = false;\r\n\r\n\t\tif (cameraDevice != null) {\r\n\t\t\tcameraDevice.stopPreview();\r\n\t\t\tcameraDevice.release();\r\n\t\t\tcameraDevice = null;\r\n\t\t}\r\n\r\n\t\tif (mWakeLock != null) {\r\n\t\t\tmWakeLock.release();\r\n\t\t\tmWakeLock = null;\r\n\t\t}\r\n\t}\r\n\r\n\r\n\tprivate void initLayout() {\r\n\r\n        /* get size of screen */\r\n\r\n        /* add control button: start and stop */\r\n\t\tbtnRecorderControl = (Button) findViewById(R.id.recorder_control);\r\n\t\tbtnRecorderControl.setText(\"Start\");\r\n\t\tbtnRecorderControl.setOnClickListener(this);\r\n\t\tbtnEffectChange = (Button) findViewById(R.id.recorder_control2);\r\n\t\tbtnEffectChange.setOnClickListener(new OnClickListener() {\r\n\t\t\t@Override\r\n\t\t\tpublic void onClick(View view) {\r\n\t\t\t\tString effect = effects.get(index++);\r\n\t\t\t\tindex %= effects.size();\r\n\t\t\t\tCamera.Parameters parameters = mCamera.getParameters();\r\n\t\t\t\tparameters.setColorEffect(effect);\r\n\t\t\t\tmCamera.setParameters(parameters);\r\n\t\t\t}\r\n\t\t});\r\n\t\tbtnSnap = (Button) findViewById(R.id.recorder_control3);\r\n\t\tbtnSnap.setOnClickListener(new OnClickListener() {\r\n\t\t\t@Override\r\n\t\t\tpublic void onClick(View view) {\r\n\t\t\t\ttoSnap = true;\r\n\t\t\t}\r\n\t\t});\r\n\t\tsurfaceView = (SurfaceView) findViewById(R.id.surface);\r\n\t\tSurfaceHolder holder = surfaceView.getHolder();\r\n\t\tholder.addCallback(this);\r\n\t\tLog.i(LOG_TAG, \"cameara preview start: OK\");\r\n\t}\r\n\r\n\t//---------------------------------------\r\n\t// initialize ffmpeg_recorder\r\n\t//---------------------------------------\r\n\tprivate void initRecorder() {\r\n\r\n\t\tLog.w(LOG_TAG, \"init recorder\");\r\n\r\n\t\tif (RECORD_LENGTH > 0) {\r\n\t\t\timagesIndex = 0;\r\n\t\t\timages = new ArrayList<>();\r\n\t\t\ttimestamps = new ArrayList<>();\r\n\t\t} else if (yuvImage == null) {\r\n\t\t\tyuvImage = new Frame(imageWidth, imageHeight, Frame.DEPTH_UBYTE, 2);\r\n\t\t\tLog.i(LOG_TAG, \"create yuvImage\");\r\n\t\t}\r\n\r\n\t\tLog.i(LOG_TAG, \"ffmpeg_url: \" + ffmpeg_link);\r\n\t\trecorder = new FFmpegFrameRecorder(ffmpeg_link, imageWidth, imageHeight, 2);\r\n\t\trecorder.setFormat(\"mp4\");\r\n\t\trecorder.setVideoCodec(avcodec.AV_CODEC_ID_H264);\r\n\t\trecorder.setGopSize(frameRate);\r\n\t\trecorder.setAspectRatio(9 / 16);\r\n\t\trecorder.setVideoBitrate(90 * 10000);\r\n\t\trecorder.setSampleRate(sampleAudioRateInHz);\r\n\t\t// Set in the surface changed method\r\n\t\trecorder.setFrameRate(frameRate);\r\n\t\trecorder.setPixelFormat(avutil.AV_PIX_FMT_YUV420P);\r\n\r\n\t\tLog.i(LOG_TAG, \"recorder initialize success\");\r\n\r\n\t\taudioRecordRunnable = new AudioRecordRunnable();\r\n\t\taudioThread = new Thread(audioRecordRunnable);\r\n\t\trunAudioThread = true;\r\n\t}\r\n\r\n\tpublic void startRecording() {\r\n\r\n\t\tinitRecorder();\r\n\r\n\t\ttry {\r\n\t\t\trecorder.start();\r\n\t\t\tstartTime = System.currentTimeMillis();\r\n\t\t\trecording = true;\r\n\t\t\taudioThread.start();\r\n\t\t\trecorderThread.start();\r\n\r\n\t\t} catch (FFmpegFrameRecorder.Exception e) {\r\n\t\t\te.printStackTrace();\r\n\t\t}\r\n\t}\r\n\r\n\tpublic void stopRecording() {\r\n\r\n\r\n\t\trunAudioThread = false;\r\n\t\ttry {\r\n\t\t\taudioThread.join();\r\n\t\t} catch (InterruptedException e) {\r\n\t\t\te.printStackTrace();\r\n\t\t}\r\n\t\taudioRecordRunnable = null;\r\n\t\taudioThread = null;\r\n\r\n\t\tif (recorder != null && recording) {\r\n\t\t\trecording = false;\r\n\t\t\tLog.v(LOG_TAG, \"Finishing recording, calling stop and release on recorder\");\r\n\t\t}\r\n\t}\r\n\r\n\t@Override\r\n\tpublic boolean onKeyDown(int keyCode, KeyEvent event) {\r\n\r\n\t\tif (keyCode == KeyEvent.KEYCODE_BACK) {\r\n\t\t\tif (recording) {\r\n\t\t\t\tstopRecording();\r\n\t\t\t}\r\n\r\n\t\t\tfinish();\r\n\r\n\t\t\treturn true;\r\n\t\t}\r\n\r\n\t\treturn super.onKeyDown(keyCode, event);\r\n\t}\r\n\r\n\r\n\t//---------------------------------------------\r\n\t// audio thread, gets and encodes audio data\r\n\t//---------------------------------------------\r\n\tclass AudioRecordRunnable implements Runnable {\r\n\r\n\t\t@Override\r\n\t\tpublic void run() {\r\n\t\t\tandroid.os.Process.setThreadPriority(android.os.Process.THREAD_PRIORITY_URGENT_AUDIO);\r\n\r\n\t\t\t// Audio\r\n\t\t\tint bufferSize;\r\n\t\t\tShortBuffer audioData;\r\n\t\t\tint bufferReadResult;\r\n\r\n\t\t\tbufferSize = AudioRecord.getMinBufferSize(sampleAudioRateInHz,\r\n\t\t\t\t\tAudioFormat.CHANNEL_IN_MONO, AudioFormat.ENCODING_PCM_16BIT);\r\n\t\t\taudioRecord = new AudioRecord(MediaRecorder.AudioSource.MIC, sampleAudioRateInHz,\r\n\t\t\t\t\tAudioFormat.CHANNEL_IN_MONO, AudioFormat.ENCODING_PCM_16BIT, bufferSize);\r\n\r\n\t\t\tif (RECORD_LENGTH > 0) {\r\n\t\t\t\tsamplesIndex = 0;\r\n\t\t\t\tsamples = new ShortBuffer[RECORD_LENGTH * sampleAudioRateInHz * 2 / bufferSize + 1];\r\n\t\t\t\tfor (int i = 0; i < samples.length; i++) {\r\n\t\t\t\t\tsamples[i] = ShortBuffer.allocate(bufferSize);\r\n\t\t\t\t}\r\n\t\t\t} else {\r\n\t\t\t\taudioData = ShortBuffer.allocate(bufferSize);\r\n\t\t\t}\r\n\r\n\t\t\tLog.d(LOG_TAG, \"audioRecord.startRecording()\");\r\n\t\t\taudioRecord.startRecording();\r\n\r\n            /* ffmpeg_audio encoding loop */\r\n\t\t\twhile (runAudioThread) {\r\n\t\t\t\tif (RECORD_LENGTH > 0) {\r\n\t\t\t\t\taudioData = samples[samplesIndex++ % samples.length];\r\n\t\t\t\t\taudioData.position(0).limit(0);\r\n\t\t\t\t}\r\n\t\t\t\t//Log.v(LOG_TAG,\"recording? \" + recording);\r\n\t\t\t\tbufferReadResult = audioRecord.read(audioData.array(), 0, audioData.capacity());\r\n\t\t\t\taudioData.limit(bufferReadResult);\r\n\t\t\t\tif (bufferReadResult > 0) {\r\n\t\t\t\t\tLog.v(LOG_TAG, \"bufferReadResult: \" + bufferReadResult);\r\n\t\t\t\t\t// If \"recording\" isn't true when start this thread, it never get's set according to this if statement...!!!\r\n\t\t\t\t\t// Why?  Good question...\r\n\t\t\t\t\tif (recording) {\r\n\t\t\t\t\t\tif (RECORD_LENGTH <= 0) try {\r\n\t\t\t\t\t\t\trecorder.recordSamples(audioData);\r\n\t\t\t\t\t\t\t//Log.v(LOG_TAG,\"recording \" + 1024*i + \" to \" + 1024*i+1024);\r\n\t\t\t\t\t\t} catch (FFmpegFrameRecorder.Exception e) {\r\n\t\t\t\t\t\t\tLog.v(LOG_TAG, e.getMessage());\r\n\t\t\t\t\t\t\te.printStackTrace();\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tLog.v(LOG_TAG, \"AudioThread Finished, release audioRecord\");\r\n\r\n            /* encoding finish, release recorder */\r\n\t\t\tif (audioRecord != null) {\r\n\t\t\t\taudioRecord.stop();\r\n\t\t\t\taudioRecord.release();\r\n\t\t\t\taudioRecord = null;\r\n\t\t\t\tLog.v(LOG_TAG, \"audioRecord released\");\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\r\n\t//---------------------------------------------\r\n\t// camera thread, gets and encodes video data\r\n\t//---------------------------------------------\r\n\r\n\tprivate SurfaceHolder mHolder;\r\n\tprivate Camera mCamera;\r\n\tprivate Camera.Size size;\r\n\tprivate boolean isCameraBack = true;\r\n\r\n\t@Override\r\n\tpublic void surfaceCreated(SurfaceHolder mHolder) {\r\n\t\tthis.mHolder = mHolder;\r\n\r\n\t\ttry {\r\n\t\t\tif (isCameraBack) {\r\n\t\t\t\tmCamera = Camera.open(Camera.CameraInfo.CAMERA_FACING_BACK);\r\n\t\t\t} else {\r\n\t\t\t\tmCamera = Camera.open(Camera.CameraInfo.CAMERA_FACING_FRONT);\r\n\t\t\t}\r\n\t\t\tmCamera.setDisplayOrientation(90);\r\n\t\t\tmCamera.setPreviewCallback(this);\r\n\t\t\tCamera.Size pictureSize = null;\r\n\t\t\tCamera.Size previewSize = null;\r\n\t\t\tCamera.Parameters parameters = mCamera.getParameters();\r\n\r\n\t\t\tList<Camera.Size> supportedPreviewSizes\r\n\t\t\t\t\t= SupportedSizesReflect.getSupportedPreviewSizes(parameters);\r\n\t\t\tList<Camera.Size> supportedVideoSizes = parameters.getSupportedVideoSizes();\r\n\t\t\tif (supportedPreviewSizes != null && supportedPreviewSizes.size() > 0) {\r\n\t\t\t\tpreviewSize = getOptimalPreviewSize(supportedPreviewSizes, 1180, 720);\r\n\r\n\t\t\t}\r\n\t\t\tif (supportedVideoSizes != null && supportedVideoSizes.size() > 0) {\r\n\t\t\t\tsize = getOptimalPreviewSize(supportedVideoSizes, 1180, 720);\r\n\t\t\t}\r\n\t\t\tif (size == null) size = previewSize;\r\n\t\t\timageWidth = previewSize.height;\r\n\t\t\timageHeight = previewSize.width;\r\n\t\t\tLogger.out(previewSize.width + \"*\" + previewSize.height);\r\n\t\t\tparameters.setPreviewSize(previewSize.width, previewSize.height);\r\n\t\t\tparameters.setRecordingHint(true);\r\n\t\t\tparameters.setPictureFormat(ImageFormat.NV21);\r\n\t\t\tparameters.setPreviewFormat(ImageFormat.NV21);\r\n\t\t\tLogger.out(\"PREVIEW_FORMATS:\" + parameters.getSupportedPreviewFormats());\r\n\t\t\teffects = parameters.getSupportedColorEffects();\r\n\t\t\tmCamera.setParameters(parameters);\r\n\t\t\tmCamera.setPreviewDisplay(mHolder);\r\n\t\t\tmCamera.startPreview();\r\n\t\t} catch (Exception e) {\r\n\t\t\te.printStackTrace();\r\n\t\t\treturn;\r\n\t\t}\r\n\t}\r\n\r\n\r\n\tprivate Camera.Size getOptimalPreviewSize(List<Camera.Size> sizes, int w, int h) {\r\n\t\tfinal double ASPECT_TOLERANCE = 0.1;\r\n\t\tdouble targetRatio = (double) w / h;\r\n\t\tif (sizes == null) return null;\r\n\r\n\t\tCamera.Size optimalSize = null;\r\n\t\tdouble minDiff = Double.MAX_VALUE;\r\n\r\n\t\tint targetHeight = h;\r\n\r\n\t\t// Try to find an size match aspect ratio and size\r\n\t\tfor (Camera.Size size : sizes) {\r\n\t\t\tdouble ratio = (double) size.width / size.height;\r\n\t\t\tif (Math.abs(ratio - targetRatio) > ASPECT_TOLERANCE) continue;\r\n\t\t\tif (Math.abs(size.height - targetHeight) < minDiff) {\r\n\t\t\t\toptimalSize = size;\r\n\t\t\t\tminDiff = Math.abs(size.height - targetHeight);\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\t// Cannot find the one match the aspect ratio, ignore the requirement\r\n\t\tif (optimalSize == null) {\r\n\t\t\tminDiff = Double.MAX_VALUE;\r\n\t\t\tfor (Camera.Size size : sizes) {\r\n\t\t\t\tif (Math.abs(size.height - targetHeight) < minDiff) {\r\n\t\t\t\t\toptimalSize = size;\r\n\t\t\t\t\tminDiff = Math.abs(size.height - targetHeight);\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t\treturn optimalSize;\r\n\t}\r\n\r\n\t@Override\r\n\tpublic void surfaceChanged(SurfaceHolder mHolder, int i, int i1, int i2) {\r\n\t\tthis.mHolder = mHolder;\r\n\t}\r\n\r\n\t@Override\r\n\tpublic void surfaceDestroyed(SurfaceHolder mHolder) {\r\n\t\tif (mCamera != null) {\r\n\t\t\tmCamera.setPreviewCallback(null);\r\n\t\t\tmCamera.stopPreview();\r\n\t\t\tmCamera.release();\r\n\t\t\tmCamera = null;\r\n\t\t}\r\n\r\n\t\tmHolder = null;\r\n\t\tif (mHolder != null) {\r\n\t\t\tmHolder = null;\r\n\t\t}\r\n\t}\r\n\r\n\t@Override\r\n\tpublic void onPreviewFrame(byte[] data, Camera camera) {\r\n\t\tif (toSnap) {\r\n\t\t\ttoSnap = false;\r\n\t\t\timage = new YuvImage(data, ImageFormat.NV21, imageHeight, imageWidth, null);\r\n\t\t\ttry {\r\n\t\t\t\tFileOutputStream fileOutputStream = new FileOutputStream(new File(\"/sdcard/test.jpg\"));\r\n\t\t\t\timage.compressToJpeg(new Rect(0, 0, imageHeight, imageWidth), 100, fileOutputStream);\r\n\t\t\t} catch (FileNotFoundException e) {\r\n\t\t\t\te.printStackTrace();\r\n\t\t\t}\r\n\t\t}\r\n\t\tif (audioRecord == null || audioRecord.getRecordingState() != AudioRecord.RECORDSTATE_RECORDING) {\r\n\t\t\tstartTime = System.currentTimeMillis();\r\n\t\t\treturn;\r\n\t\t}\r\n\t\tif (RECORD_LENGTH > 0) {\r\n\t\t\tint i = imagesIndex++ % roller_length;\r\n\t\t\tyuvImage = new Frame(imageWidth, imageHeight, Frame.DEPTH_UBYTE, 2);\r\n\t\t\timages.add(yuvImage);\r\n\t\t\ttimestamps[i] = 1000 * (System.currentTimeMillis() - startTime);\r\n\t\t}\r\n\t\t\t/* get video data */\r\n\t\tif (recording) {\r\n\t\t\tyuvImage = new Frame(imageWidth, imageHeight, Frame.DEPTH_UBYTE, 2);\r\n\t\t\t((ByteBuffer) yuvImage.image[0].position(0)).put(rotateYUV420Degree90(data, imageHeight, imageWidth));\r\n\t\t\ttimestamps.add(1000 * (System.currentTimeMillis() - startTime));\r\n\t\t\timages.add(yuvImage);\r\n\r\n\t\t\tif (RECORD_LENGTH <= 0) try {\r\n\t\t\t\tLog.v(LOG_TAG, \"Writing Frame\");\r\n\t\t\t\tlong t = 1000 * (System.currentTimeMillis() - startTime);\r\n\t\t\t\tif (t > recorder.getTimestamp()) {\r\n\t\t\t\t\trecorder.setTimestamp(t);\r\n\t\t\t\t}\r\n\t\t\t\trecorder.record(yuvImage);\r\n\t\t\t} catch (FFmpegFrameRecorder.Exception e) {\r\n\t\t\t\tLog.v(LOG_TAG, e.getMessage());\r\n\t\t\t\te.printStackTrace();\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\r\n\t@Override\r\n\tpublic void onClick(View v) {\r\n\t\tif (!recording) {\r\n\t\t\tstartRecording();\r\n\t\t\tLog.w(LOG_TAG, \"Start Button Pushed\");\r\n\t\t\tbtnRecorderControl.setText(\"Stop\");\r\n\t\t} else {\r\n\t\t\t// This will trigger the audio recording loop to stop and then set isRecorderStart = false;\r\n\t\t\tstopRecording();\r\n\t\t\tLog.w(LOG_TAG, \"Stop Button Pushed\");\r\n\t\t\tbtnRecorderControl.setText(\"Start\");\r\n\t\t}\r\n\t}\r\n\r\n\tThread recorderThread = new Thread() {\r\n\t\tint index = 0;\r\n\r\n\t\t@Override\r\n\t\tpublic void run() {\r\n\t\t\tLogger.out(\"RECORD_THREAD_START\");\r\n\t\t\twhile (images.size() != 0 || recording) {\r\n\t\t\t\ttry {\r\n\t\t\t\t\tif (images.size() > 0) {\r\n\t\t\t\t\t\tLogger.out(\"record_start_\" + index);\r\n\t\t\t\t\t\tlong t = timestamps.get(0);\r\n\t\t\t\t\t\tif (t >= 0) {\r\n\t\t\t\t\t\t\tif (t > recorder.getTimestamp()) {\r\n\t\t\t\t\t\t\t\trecorder.setTimestamp(t);\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t\trecorder.record(images.get(0));\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\ttimestamps.remove(0);\r\n\t\t\t\t\t\timages.remove(0);\r\n\t\t\t\t\t\tLogger.out(\"record_end_\" + index++);\r\n\t\t\t\t\t}\r\n\t\t\t\t} catch (FrameRecorder.Exception e) {\r\n\t\t\t\t\te.printStackTrace();\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tif (!recording) {\r\n\t\t\t\ttry {\r\n\t\t\t\t\trecorder.stop();\r\n\t\t\t\t\trecorder.release();\r\n\t\t\t\t} catch (FFmpegFrameRecorder.Exception e) {\r\n\t\t\t\t\te.printStackTrace();\r\n\t\t\t\t}\r\n\t\t\t\trecorder = null;\r\n\t\t\t\tLogger.out(\"FFMPEGRECORDER_RELEASED\");\r\n\t\t\t\tstartUploadingVideo(ffmpeg_link);\r\n\t\t\t}\r\n\r\n\t\t}\r\n\t};"},"comment":{"url":"https://api.github.com/repos/bytedeco/javacv/issues/comments/141378916","html_url":"https://github.com/bytedeco/javacv/issues/224#issuecomment-141378916","issue_url":"https://api.github.com/repos/bytedeco/javacv/issues/224","id":141378916,"user":{"login":"ProgrammerYuan","id":5723923,"avatar_url":"https://avatars.githubusercontent.com/u/5723923?v=3","gravatar_id":"","url":"https://api.github.com/users/ProgrammerYuan","html_url":"https://github.com/ProgrammerYuan","followers_url":"https://api.github.com/users/ProgrammerYuan/followers","following_url":"https://api.github.com/users/ProgrammerYuan/following{/other_user}","gists_url":"https://api.github.com/users/ProgrammerYuan/gists{/gist_id}","starred_url":"https://api.github.com/users/ProgrammerYuan/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/ProgrammerYuan/subscriptions","organizations_url":"https://api.github.com/users/ProgrammerYuan/orgs","repos_url":"https://api.github.com/users/ProgrammerYuan/repos","events_url":"https://api.github.com/users/ProgrammerYuan/events{/privacy}","received_events_url":"https://api.github.com/users/ProgrammerYuan/received_events","type":"User","site_admin":false},"created_at":"2015-09-18T08:18:47Z","updated_at":"2015-09-18T08:18:47Z","body":"Also, when I want to convert nv21 format frame to YUV420P,it goes wrong, the whole picture becomes grey,green and pink..."}}