Jelajahi Sumber

Merge pull request #3415 from jpark37/default-color-space

Unify color space settings as 709
Jim 5 tahun lalu
induk
melakukan
86147d9719

+ 1 - 1
UI/window-basic-main.cpp

@@ -1392,7 +1392,7 @@ bool OBSBasic::InitBasicConfigDefaults()
 	config_set_default_uint(basicConfig, "Video", "FPSDen", 1);
 	config_set_default_string(basicConfig, "Video", "ScaleType", "bicubic");
 	config_set_default_string(basicConfig, "Video", "ColorFormat", "NV12");
-	config_set_default_string(basicConfig, "Video", "ColorSpace", "sRGB");
+	config_set_default_string(basicConfig, "Video", "ColorSpace", "709");
 	config_set_default_string(basicConfig, "Video", "ColorRange",
 				  "Partial");
 

+ 9 - 3
deps/media-playback/media-playback/media.c

@@ -112,12 +112,18 @@ static inline enum speaker_layout convert_speaker_layout(uint8_t channels)
 static inline enum video_colorspace
 convert_color_space(enum AVColorSpace s, enum AVColorTransferCharacteristic trc)
 {
-	if (s == AVCOL_SPC_BT709) {
+	switch (s) {
+	case AVCOL_SPC_BT709:
 		return (trc == AVCOL_TRC_IEC61966_2_1) ? VIDEO_CS_SRGB
 						       : VIDEO_CS_709;
+	case AVCOL_SPC_FCC:
+	case AVCOL_SPC_BT470BG:
+	case AVCOL_SPC_SMPTE170M:
+	case AVCOL_SPC_SMPTE240M:
+		return VIDEO_CS_601;
+	default:
+		return VIDEO_CS_DEFAULT;
 	}
-
-	return VIDEO_CS_DEFAULT;
 }
 
 static inline enum video_range_type convert_color_range(enum AVColorRange r)

+ 2 - 1
docs/sphinx/reference-libobs-media-io.rst

@@ -39,9 +39,10 @@ Video Handler
 
    YUV color space.  Can be one of the following values:
 
-   - VIDEO_CS_DEFAULT - Equivalent to VIDEO_CS_601
+   - VIDEO_CS_DEFAULT - Equivalent to VIDEO_CS_709
    - VIDEO_CS_601     - 601 color space
    - VIDEO_CS_709     - 709 color space
+   - VIDEO_CS_SRGB    - sRGB color space
 
 ---------------------
 

+ 1 - 0
docs/sphinx/reference-outputs.rst

@@ -686,6 +686,7 @@ Functions used by outputs
            VIDEO_CS_DEFAULT,
            VIDEO_CS_601,
            VIDEO_CS_709,
+           VIDEO_CS_SRGB,
    };
    
    enum video_range_type {

+ 2 - 2
libobs/media-io/video-io.h

@@ -174,12 +174,12 @@ static inline const char *get_video_format_name(enum video_format format)
 static inline const char *get_video_colorspace_name(enum video_colorspace cs)
 {
 	switch (cs) {
+	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_709:
 		return "709";
 	case VIDEO_CS_SRGB:
 		return "sRGB";
-	case VIDEO_CS_601:
-	case VIDEO_CS_DEFAULT:;
+	case VIDEO_CS_601:;
 	}
 
 	return "601";

+ 1 - 3
libobs/media-io/video-matrices.c

@@ -171,9 +171,7 @@ bool video_format_get_parameters(enum video_colorspace color_space,
 		matrices_initialized = true;
 	}
 #endif
-	if (color_space == VIDEO_CS_DEFAULT)
-		color_space = VIDEO_CS_601;
-	else if (color_space == VIDEO_CS_SRGB)
+	if ((color_space == VIDEO_CS_DEFAULT) || (color_space == VIDEO_CS_SRGB))
 		color_space = VIDEO_CS_709;
 
 	for (size_t i = 0; i < NUM_FORMATS; i++) {

+ 3 - 9
libobs/media-io/video-scaler-ffmpeg.c

@@ -91,15 +91,9 @@ static inline int get_ffmpeg_scale_type(enum video_scale_type type)
 
 static inline const int *get_ffmpeg_coeffs(enum video_colorspace cs)
 {
-	switch (cs) {
-	case VIDEO_CS_709:
-	case VIDEO_CS_SRGB:
-		return sws_getCoefficients(SWS_CS_ITU709);
-	case VIDEO_CS_DEFAULT:
-	case VIDEO_CS_601:
-	default:
-		return sws_getCoefficients(SWS_CS_ITU601);
-	}
+	const int colorspace = (cs == VIDEO_CS_601) ? SWS_CS_ITU601
+						    : SWS_CS_ITU709;
+	return sws_getCoefficients(colorspace);
 }
 
 static inline int get_ffmpeg_range_type(enum video_range_type type)

+ 1 - 1
plugins/decklink/decklink-device-instance.cpp

@@ -192,7 +192,7 @@ void DeckLinkDeviceInstance::SetupVideoFormat(DeckLinkDeviceMode *mode_)
 #ifdef LOG_SETUP_VIDEO_FORMAT
 	LOG(LOG_INFO, "Setup video format: %s, %s, %s",
 	    pixelFormat == bmdFormat8BitYUV ? "YUV" : "RGB",
-	    activeColorSpace == VIDEO_CS_709 ? "BT.709" : "BT.601",
+	    activeColorSpace == VIDEO_CS_601 ? "BT.601" : "BT.709",
 	    colorRange == VIDEO_RANGE_FULL ? "full" : "limited");
 #endif
 }

+ 1 - 1
plugins/enc-amf

@@ -1 +1 @@
-Subproject commit 6e934b6b281cf675522ea43391376bd6bb089256
+Subproject commit 272f0ffb70e489a48d1859b1bf7291931ff1ee9b

+ 3 - 3
plugins/mac-avcapture/av-capture.mm

@@ -442,11 +442,11 @@ static inline video_colorspace get_colorspace(CMFormatDescriptionRef desc)
 		return VIDEO_CS_DEFAULT;
 
 	if (CFStringCompare(static_cast<CFStringRef>(matrix),
-			    kCVImageBufferYCbCrMatrix_ITU_R_709_2,
+			    kCVImageBufferYCbCrMatrix_ITU_R_601_4,
 			    0) == kCFCompareEqualTo)
-		return VIDEO_CS_709;
+		return VIDEO_CS_601;
 
-	return VIDEO_CS_601;
+	return VIDEO_CS_709;
 }
 
 static inline bool update_colorspace(av_capture *capture,

+ 1 - 1
plugins/obs-ffmpeg/jim-nvenc.c

@@ -431,12 +431,12 @@ static bool init_encoder(struct nvenc_data *enc, obs_data_t *settings)
 	vui_params->colourDescriptionPresentFlag = 1;
 
 	switch (voi->colorspace) {
-	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_601:
 		vui_params->colourPrimaries = 6;
 		vui_params->transferCharacteristics = 6;
 		vui_params->colourMatrix = 6;
 		break;
+	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_709:
 		vui_params->colourPrimaries = 1;
 		vui_params->transferCharacteristics = 1;

+ 1 - 1
plugins/obs-ffmpeg/obs-ffmpeg-mux.c

@@ -160,12 +160,12 @@ static void add_video_encoder_params(struct ffmpeg_muxer *stream,
 	enum AVColorTransferCharacteristic trc = AVCOL_TRC_UNSPECIFIED;
 	enum AVColorSpace spc = AVCOL_SPC_UNSPECIFIED;
 	switch (info->colorspace) {
-	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_601:
 		pri = AVCOL_PRI_SMPTE170M;
 		trc = AVCOL_TRC_SMPTE170M;
 		spc = AVCOL_SPC_SMPTE170M;
 		break;
+	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_709:
 		pri = AVCOL_PRI_BT709;
 		trc = AVCOL_TRC_BT709;

+ 1 - 1
plugins/obs-ffmpeg/obs-ffmpeg-nvenc.c

@@ -241,12 +241,12 @@ static bool nvenc_update(void *data, obs_data_t *settings)
 	enc->context->max_b_frames = bf;
 
 	switch (info.colorspace) {
-	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_601:
 		enc->context->color_trc = AVCOL_TRC_SMPTE170M;
 		enc->context->color_primaries = AVCOL_PRI_SMPTE170M;
 		enc->context->colorspace = AVCOL_SPC_SMPTE170M;
 		break;
+	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_709:
 		enc->context->color_trc = AVCOL_TRC_BT709;
 		enc->context->color_primaries = AVCOL_PRI_BT709;

+ 4 - 13
plugins/obs-ffmpeg/obs-ffmpeg-output.c

@@ -1088,11 +1088,11 @@ static bool try_connect(struct ffmpeg_output *output)
 	config.color_range = voi->range == VIDEO_RANGE_FULL ? AVCOL_RANGE_JPEG
 							    : AVCOL_RANGE_MPEG;
 	switch (voi->colorspace) {
-	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_601:
 		config.color_primaries = AVCOL_PRI_SMPTE170M;
 		config.color_trc = AVCOL_TRC_SMPTE170M;
 		break;
+	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_709:
 		config.color_primaries = AVCOL_PRI_BT709;
 		config.color_trc = AVCOL_TRC_BT709;
@@ -1104,18 +1104,9 @@ static bool try_connect(struct ffmpeg_output *output)
 	}
 
 	if (format_is_yuv(voi->format)) {
-		switch (voi->colorspace) {
-		case VIDEO_CS_DEFAULT:
-		case VIDEO_CS_601:
-			config.colorspace = AVCOL_SPC_SMPTE170M;
-			break;
-		case VIDEO_CS_709:
-			config.colorspace = AVCOL_SPC_BT709;
-			break;
-		case VIDEO_CS_SRGB:
-			config.colorspace = AVCOL_SPC_BT709;
-			break;
-		}
+		config.colorspace = (voi->colorspace == VIDEO_CS_601)
+					    ? AVCOL_SPC_SMPTE170M
+					    : AVCOL_SPC_BT709;
 	} else {
 		config.colorspace = AVCOL_SPC_RGB;
 	}

+ 19 - 3
plugins/obs-ffmpeg/obs-ffmpeg-vaapi.c

@@ -244,13 +244,29 @@ static bool vaapi_update(void *data, obs_data_t *settings)
 
 	enc->context->time_base = (AVRational){voi->fps_den, voi->fps_num};
 	enc->context->pix_fmt = obs_to_ffmpeg_video_format(info.format);
-	enc->context->colorspace = info.colorspace == VIDEO_CS_709
-					   ? AVCOL_SPC_BT709
-					   : AVCOL_SPC_BT470BG;
 	enc->context->color_range = info.range == VIDEO_RANGE_FULL
 					    ? AVCOL_RANGE_JPEG
 					    : AVCOL_RANGE_MPEG;
 
+	switch (info.colorspace) {
+	case VIDEO_CS_601:
+		enc->context->color_trc = AVCOL_TRC_SMPTE170M;
+		enc->context->color_primaries = AVCOL_PRI_SMPTE170M;
+		enc->context->colorspace = AVCOL_SPC_SMPTE170M;
+		break;
+	case VIDEO_CS_DEFAULT:
+	case VIDEO_CS_709:
+		enc->context->color_trc = AVCOL_TRC_BT709;
+		enc->context->color_primaries = AVCOL_PRI_BT709;
+		enc->context->colorspace = AVCOL_SPC_BT709;
+		break;
+	case VIDEO_CS_SRGB:
+		enc->context->color_trc = AVCOL_TRC_IEC61966_2_1;
+		enc->context->color_primaries = AVCOL_PRI_BT709;
+		enc->context->colorspace = AVCOL_SPC_BT709;
+		break;
+	}
+
 	if (keyint_sec > 0) {
 		enc->context->gop_size =
 			keyint_sec * voi->fps_num / voi->fps_den;

+ 1 - 1
plugins/obs-x264/obs-x264.c

@@ -468,12 +468,12 @@ static void update_params(struct obs_x264 *obsx264, obs_data_t *settings,
 	const char *transfer = NULL;
 	const char *colmatrix = NULL;
 	switch (info.colorspace) {
-	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_601:
 		colorprim = smpte170m;
 		transfer = smpte170m;
 		colmatrix = smpte170m;
 		break;
+	case VIDEO_CS_DEFAULT:
 	case VIDEO_CS_709:
 		colorprim = bt709;
 		transfer = bt709;

+ 31 - 13
plugins/win-dshow/ffmpeg-decode.c

@@ -270,6 +270,23 @@ bool ffmpeg_decode_audio(struct ffmpeg_decode *decode, uint8_t *data,
 	return true;
 }
 
+static enum video_colorspace
+convert_color_space(enum AVColorSpace s, enum AVColorTransferCharacteristic trc)
+{
+	switch (s) {
+	case AVCOL_SPC_BT709:
+		return (trc == AVCOL_TRC_IEC61966_2_1) ? VIDEO_CS_SRGB
+						       : VIDEO_CS_709;
+	case AVCOL_SPC_FCC:
+	case AVCOL_SPC_BT470BG:
+	case AVCOL_SPC_SMPTE170M:
+	case AVCOL_SPC_SMPTE240M:
+		return VIDEO_CS_601;
+	default:
+		return VIDEO_CS_DEFAULT;
+	}
+}
+
 bool ffmpeg_decode_video(struct ffmpeg_decode *decode, uint8_t *data,
 			 size_t size, long long *ts,
 			 enum video_range_type range,
@@ -344,21 +361,22 @@ bool ffmpeg_decode_video(struct ffmpeg_decode *decode, uint8_t *data,
 				: VIDEO_RANGE_PARTIAL;
 	}
 
-	if (range != frame->range) {
-		const bool success = video_format_get_parameters(
-			VIDEO_CS_601, range, frame->color_matrix,
-			frame->color_range_min, frame->color_range_max);
-		if (!success) {
-			blog(LOG_ERROR,
-			     "Failed to get video format "
-			     "parameters for video format %u",
-			     VIDEO_CS_601);
-			return false;
-		}
-
-		frame->range = range;
+	const enum video_colorspace cs = convert_color_space(
+		decode->frame->colorspace, decode->frame->color_trc);
+
+	const bool success = video_format_get_parameters(
+		cs, range, frame->color_matrix, frame->color_range_min,
+		frame->color_range_max);
+	if (!success) {
+		blog(LOG_ERROR,
+		     "Failed to get video format "
+		     "parameters for video format %u",
+		     cs);
+		return false;
 	}
 
+	frame->range = range;
+
 	*ts = decode->frame->pkt_pts;
 
 	frame->width = decode->frame->width;

+ 4 - 4
plugins/win-dshow/win-dshow.cpp

@@ -1072,11 +1072,11 @@ DShowInput::GetColorSpace(obs_data_t *settings) const
 
 	if (astrcmpi(space, "709") == 0)
 		return VIDEO_CS_709;
-	else if (astrcmpi(space, "601") == 0)
+
+	if (astrcmpi(space, "601") == 0)
 		return VIDEO_CS_601;
-	else
-		return (videoConfig.format == VideoFormat::HDYC) ? VIDEO_CS_709
-								 : VIDEO_CS_601;
+
+	return VIDEO_CS_DEFAULT;
 }
 
 inline enum video_range_type