Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorThomas Beck <software@plasmasolutions.de>2015-12-28 13:55:14 +0300
committerThomas Beck <software@plasmasolutions.de>2015-12-28 14:16:48 +0300
commitdaf6f5f81e241484ea8afc5d70ef3027969e5ac1 (patch)
tree723d322d646da66ce8beda142b493652463d9422 /source/blender/blenkernel/intern/seqmodifier.c
parent225b02fcd66052b1d6dfa4a146798e41c44e0cd4 (diff)
White Balance modifier for the VSE
This snippet creates a white balance modifier for the video sequence editor. It is useful for everyone who likes to set a new white point in the video source (easily via the eyedropper). Just select a point in the source file where you know that it should be white. The algorithm will then shift the colors towards your new white point. See attached the image for a quick demo. {F270576} Reviewers: psy-fi Reviewed By: psy-fi Subscribers: Blendify Projects: #bf_blender Differential Revision: https://developer.blender.org/D1698
Diffstat (limited to 'source/blender/blenkernel/intern/seqmodifier.c')
-rw-r--r--source/blender/blenkernel/intern/seqmodifier.c87
1 files changed, 86 insertions, 1 deletions
diff --git a/source/blender/blenkernel/intern/seqmodifier.c b/source/blender/blenkernel/intern/seqmodifier.c
index 07242aa2f6e..f12faacd677 100644
--- a/source/blender/blenkernel/intern/seqmodifier.c
+++ b/source/blender/blenkernel/intern/seqmodifier.c
@@ -42,12 +42,14 @@
#include "BLT_translation.h"
#include "DNA_sequence_types.h"
+#include "DNA_scene_types.h"
#include "BKE_colortools.h"
#include "BKE_sequencer.h"
#include "IMB_imbuf.h"
#include "IMB_imbuf_types.h"
+#include "IMB_colormanagement.h"
static SequenceModifierTypeInfo *modifiersTypes[NUM_SEQUENCE_MODIFIER_TYPES];
static bool modifierTypesInit = false;
@@ -173,6 +175,87 @@ static SequenceModifierTypeInfo seqModifier_ColorBalance = {
colorBalance_apply /* apply */
};
+/* **** White Balance Modifier **** */
+
+static void whiteBalance_init_data(SequenceModifierData *smd)
+{
+ WhiteBalanceModifierData *cbmd = (WhiteBalanceModifierData *) smd;
+ copy_v3_fl(cbmd->white_value, 1.0f);
+}
+
+typedef struct WhiteBalanceThreadData {
+ struct ColorSpace* colorspace;
+ float white[3];
+} WhiteBalanceThreadData;
+
+static void whiteBalance_apply_threaded(int width, int height, unsigned char *rect, float *rect_float,
+ unsigned char *mask_rect, float *mask_rect_float, void *data_v)
+{
+ int x, y;
+ float multiplier[3];
+
+ WhiteBalanceThreadData *data = (WhiteBalanceThreadData *) data_v;
+
+ multiplier[0] = 1.0f/data->white[0];
+ multiplier[1] = 1.0f/data->white[1];
+ multiplier[2] = 1.0f/data->white[2];
+
+ for (y = 0; y < height; y++) {
+ for (x = 0; x < width; x++) {
+ int pixel_index = (y * width + x) * 4;
+ float result[3], mask[3] = {1.0f, 1.0f, 1.0f};
+
+ if (rect_float)
+ copy_v3_v3(result, rect_float + pixel_index);
+ else
+ {
+ straight_uchar_to_premul_float(result, rect + pixel_index);
+ IMB_colormanagement_colorspace_to_scene_linear_v3(result, data->colorspace);
+ }
+
+ mul_v3_v3(result, multiplier);
+
+ if (mask_rect_float)
+ copy_v3_v3(mask, mask_rect_float + pixel_index);
+ else if (mask_rect)
+ rgb_uchar_to_float(mask, mask_rect + pixel_index);
+
+ result[0] = result[0] * (1.0f - mask[0]) + result[0] * mask[0];
+ result[1] = result[1] * (1.0f - mask[1]) + result[1] * mask[1];
+ result[2] = result[2] * (1.0f - mask[2]) + result[2] * mask[2];
+
+ if (rect_float)
+ copy_v3_v3(rect_float + pixel_index, result);
+ else
+ IMB_colormanagement_scene_linear_to_colorspace_v3(result, data->colorspace);
+ premul_float_to_straight_uchar(rect + pixel_index, result);
+ }
+ }
+}
+
+static void whiteBalance_apply(SequenceModifierData *smd, ImBuf *ibuf, ImBuf *mask)
+{
+ WhiteBalanceThreadData data;
+ WhiteBalanceModifierData *wbmd = (WhiteBalanceModifierData *) smd;
+
+ copy_v3_v3(data.white, wbmd->white_value);
+ IMB_colormanagement_display_to_scene_linear_v3(data.white,
+ IMB_colormanagement_display_get_named(wbmd->modifier.scene->display_settings.display_device));
+ data.colorspace = ibuf->rect_colorspace;
+
+ modifier_apply_threaded(ibuf, mask, whiteBalance_apply_threaded, &data);
+}
+
+static SequenceModifierTypeInfo seqModifier_WhiteBalance = {
+ CTX_N_(BLT_I18NCONTEXT_ID_SEQUENCE, "White Balance"), /* name */
+ "WhiteBalanceModifierData", /* struct_name */
+ sizeof(WhiteBalanceModifierData), /* struct_size */
+ whiteBalance_init_data, /* init_data */
+ NULL, /* free_data */
+ NULL, /* copy_data */
+ whiteBalance_apply /* apply */
+};
+
/* **** Curves Modifier **** */
static void curves_init_data(SequenceModifierData *smd)
@@ -559,6 +642,7 @@ static void sequence_modifier_type_info_init(void)
INIT_TYPE(HueCorrect);
INIT_TYPE(BrightContrast);
INIT_TYPE(Mask);
+ INIT_TYPE(WhiteBalance);
#undef INIT_TYPE
}
@@ -573,7 +657,7 @@ const SequenceModifierTypeInfo *BKE_sequence_modifier_type_info_get(int type)
return modifiersTypes[type];
}
-SequenceModifierData *BKE_sequence_modifier_new(Sequence *seq, const char *name, int type)
+SequenceModifierData *BKE_sequence_modifier_new(Sequence *seq, const char *name, int type, struct Scene *scene)
{
SequenceModifierData *smd;
const SequenceModifierTypeInfo *smti = BKE_sequence_modifier_type_info_get(type);
@@ -582,6 +666,7 @@ SequenceModifierData *BKE_sequence_modifier_new(Sequence *seq, const char *name,
smd->type = type;
smd->flag |= SEQUENCE_MODIFIER_EXPANDED;
+ smd->scene = scene;
if (!name || !name[0])
BLI_strncpy(smd->name, smti->name, sizeof(smd->name));