Browse Source

Make OBS basic and obs-ffmpeg-output use NV12 by default

Palana 11 years ago
parent
commit
42be968759
2 changed files with 17 additions and 9 deletions
  1. 2 1
      obs/window-basic-main.cpp
  2. 15 8
      plugins/obs-ffmpeg/obs-ffmpeg-output.c

+ 2 - 1
obs/window-basic-main.cpp

@@ -417,7 +417,8 @@ bool OBSBasic::ResetVideo()
 			"Video", "OutputCX");
 	ovi.output_height  = (uint32_t)config_get_uint(basicConfig,
 			"Video", "OutputCY");
-	ovi.output_format  = VIDEO_FORMAT_I420;
+	//ovi.output_format  = VIDEO_FORMAT_I420;
+	ovi.output_format  = VIDEO_FORMAT_NV12;
 	ovi.adapter        = 0;
 	ovi.gpu_conversion = true;
 

+ 15 - 8
plugins/obs-ffmpeg/obs-ffmpeg-output.c

@@ -26,6 +26,9 @@
 #include <libavformat/avformat.h>
 #include <libswscale/swscale.h>
 
+//#define OBS_FFMPEG_VIDEO_FORMAT VIDEO_FORMAT_I420
+#define OBS_FFMPEG_VIDEO_FORMAT VIDEO_FORMAT_NV12
+
 /* NOTE: much of this stuff is test stuff that was more or less copied from
  * the muxing.c ffmpeg example */
 
@@ -177,8 +180,9 @@ static bool open_video_codec(struct ffmpeg_data *data)
 
 static bool init_swscale(struct ffmpeg_data *data, AVCodecContext *context)
 {
+	enum AVPixelFormat format = obs_to_ffmpeg_video_format(OBS_FFMPEG_VIDEO_FORMAT);
 	data->swscale = sws_getContext(
-			context->width, context->height, AV_PIX_FMT_YUV420P,
+			context->width, context->height, format,
 			context->width, context->height, context->pix_fmt,
 			SWS_BICUBIC, NULL, NULL, NULL);
 
@@ -214,7 +218,7 @@ static bool create_video_stream(struct ffmpeg_data *data)
 	context->time_base.num  = ovi.fps_den;
 	context->time_base.den  = ovi.fps_num;
 	context->gop_size       = 120;
-	context->pix_fmt        = AV_PIX_FMT_YUV420P;
+	context->pix_fmt        = obs_to_ffmpeg_video_format(OBS_FFMPEG_VIDEO_FORMAT);
 
 	if (data->output->oformat->flags & AVFMT_GLOBALHEADER)
 		context->flags |= CODEC_FLAG_GLOBAL_HEADER;
@@ -222,7 +226,8 @@ static bool create_video_stream(struct ffmpeg_data *data)
 	if (!open_video_codec(data))
 		return false;
 
-	if (context->pix_fmt != AV_PIX_FMT_YUV420P)
+	enum AVPixelFormat format = obs_to_ffmpeg_video_format(OBS_FFMPEG_VIDEO_FORMAT);
+	if (context->pix_fmt != format)
 		if (!init_swscale(data, context))
 			return false;
 
@@ -487,12 +492,13 @@ static inline int64_t rescale_ts(int64_t val, AVCodecContext *context,
 			AV_ROUND_NEAR_INF | AV_ROUND_PASS_MINMAX);
 }
 
-#define YUV420_PLANES 3
-
 static inline void copy_data(AVPicture *pic, const struct video_data *frame,
 		int height)
 {
-	for (int plane = 0; plane < YUV420_PLANES; plane++) {
+	for (int plane = 0; plane < MAX_AV_PLANES; plane++) {
+		if (!frame->data[plane])
+			continue;
+
 		int frame_rowsize = (int)frame->linesize[plane];
 		int pic_rowsize   = pic->linesize[plane];
 		int bytes = frame_rowsize < pic_rowsize ?
@@ -523,7 +529,8 @@ static void receive_video(void *param, struct video_data *frame)
 	if (!data->start_timestamp)
 		data->start_timestamp = frame->timestamp;
 
-	if (context->pix_fmt != AV_PIX_FMT_YUV420P)
+	enum AVPixelFormat format = obs_to_ffmpeg_video_format(OBS_FFMPEG_VIDEO_FORMAT);
+	if (context->pix_fmt != format)
 		sws_scale(data->swscale, (const uint8_t *const *)frame->data,
 				(const int*)frame->linesize,
 				0, context->height, data->dst_picture.data,
@@ -761,7 +768,7 @@ static bool try_connect(struct ffmpeg_output *output)
 	};
 
 	struct video_scale_info vsi = {
-		.format = VIDEO_FORMAT_I420
+		.format = OBS_FFMPEG_VIDEO_FORMAT
 	};
 
 	output->active = true;