mirror of
https://github.com/lovell/sharp.git
synced 2025-12-19 07:15:08 +01:00
Allow override of EXIF Orientation tag #189
Clear Orientation when rotate/flip/flop are used
This commit is contained in:
@@ -25,6 +25,8 @@
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#define EXIF_IFD0_ORIENTATION "exif-ifd0-Orientation"
|
||||
|
||||
namespace sharp {
|
||||
|
||||
// How many tasks are in the queue?
|
||||
@@ -141,14 +143,30 @@ namespace sharp {
|
||||
int orientation = 0;
|
||||
const char *exif;
|
||||
if (
|
||||
vips_image_get_typeof(image, "exif-ifd0-Orientation") != 0 &&
|
||||
!vips_image_get_string(image, "exif-ifd0-Orientation", &exif)
|
||||
vips_image_get_typeof(image, EXIF_IFD0_ORIENTATION) != 0 &&
|
||||
!vips_image_get_string(image, EXIF_IFD0_ORIENTATION, &exif)
|
||||
) {
|
||||
orientation = atoi(&exif[0]);
|
||||
}
|
||||
return orientation;
|
||||
}
|
||||
|
||||
/*
|
||||
Set EXIF Orientation of image.
|
||||
*/
|
||||
void SetExifOrientation(VipsImage *image, int const orientation) {
|
||||
char exif[3];
|
||||
g_snprintf(exif, sizeof(exif), "%d", orientation);
|
||||
vips_image_set_string(image, EXIF_IFD0_ORIENTATION, exif);
|
||||
}
|
||||
|
||||
/*
|
||||
Remove EXIF Orientation from image.
|
||||
*/
|
||||
void RemoveExifOrientation(VipsImage *image) {
|
||||
vips_image_remove(image, EXIF_IFD0_ORIENTATION);
|
||||
}
|
||||
|
||||
/*
|
||||
Returns the window size for the named interpolator. For example,
|
||||
a window size of 3 means a 3x3 pixel grid is used for the calculation.
|
||||
|
||||
10
src/common.h
10
src/common.h
@@ -64,6 +64,16 @@ namespace sharp {
|
||||
*/
|
||||
int ExifOrientation(VipsImage const *image);
|
||||
|
||||
/*
|
||||
Set EXIF Orientation of image.
|
||||
*/
|
||||
void SetExifOrientation(VipsImage *image, int const orientation);
|
||||
|
||||
/*
|
||||
Remove EXIF Orientation from image.
|
||||
*/
|
||||
void RemoveExifOrientation(VipsImage *image);
|
||||
|
||||
/*
|
||||
Returns the window size for the named interpolator. For example,
|
||||
a window size of 3 means a 3x3 pixel grid is used for the calculation.
|
||||
|
||||
@@ -36,6 +36,8 @@ using sharp::InterpolatorWindowSize;
|
||||
using sharp::HasProfile;
|
||||
using sharp::HasAlpha;
|
||||
using sharp::ExifOrientation;
|
||||
using sharp::SetExifOrientation;
|
||||
using sharp::RemoveExifOrientation;
|
||||
using sharp::IsJpeg;
|
||||
using sharp::IsPng;
|
||||
using sharp::IsWebp;
|
||||
@@ -109,6 +111,7 @@ struct PipelineBaton {
|
||||
bool optimiseScans;
|
||||
std::string err;
|
||||
bool withMetadata;
|
||||
int withMetadataOrientation;
|
||||
int tileSize;
|
||||
int tileOverlap;
|
||||
|
||||
@@ -142,6 +145,7 @@ struct PipelineBaton {
|
||||
overshootDeringing(false),
|
||||
optimiseScans(false),
|
||||
withMetadata(false),
|
||||
withMetadataOrientation(-1),
|
||||
tileSize(256),
|
||||
tileOverlap(0) {
|
||||
background[0] = 0.0;
|
||||
@@ -246,6 +250,7 @@ class PipelineWorker : public NanAsyncWorker {
|
||||
}
|
||||
vips_object_local(hook, rotated);
|
||||
image = rotated;
|
||||
RemoveExifOrientation(image);
|
||||
}
|
||||
|
||||
// Pre extraction
|
||||
@@ -563,6 +568,7 @@ class PipelineWorker : public NanAsyncWorker {
|
||||
}
|
||||
vips_object_local(hook, rotated);
|
||||
image = rotated;
|
||||
RemoveExifOrientation(image);
|
||||
}
|
||||
|
||||
// Flip (mirror about Y axis)
|
||||
@@ -573,6 +579,7 @@ class PipelineWorker : public NanAsyncWorker {
|
||||
}
|
||||
vips_object_local(hook, flipped);
|
||||
image = flipped;
|
||||
RemoveExifOrientation(image);
|
||||
}
|
||||
|
||||
// Flop (mirror about X axis)
|
||||
@@ -583,6 +590,7 @@ class PipelineWorker : public NanAsyncWorker {
|
||||
}
|
||||
vips_object_local(hook, flopped);
|
||||
image = flopped;
|
||||
RemoveExifOrientation(image);
|
||||
}
|
||||
|
||||
// Crop/embed
|
||||
@@ -801,6 +809,11 @@ class PipelineWorker : public NanAsyncWorker {
|
||||
}
|
||||
}
|
||||
|
||||
// Override EXIF Orientation tag
|
||||
if (baton->withMetadata && baton->withMetadataOrientation != -1) {
|
||||
SetExifOrientation(image, baton->withMetadataOrientation);
|
||||
}
|
||||
|
||||
#if !(VIPS_MAJOR_VERSION >= 8 || (VIPS_MAJOR_VERSION >= 7 && VIPS_MINOR_VERSION >= 40 && VIPS_MINOR_VERSION >= 5))
|
||||
// Generate image tile cache when interlace output is required - no longer required as of libvips 7.40.5+
|
||||
if (baton->progressive) {
|
||||
@@ -1194,6 +1207,7 @@ NAN_METHOD(pipeline) {
|
||||
baton->overshootDeringing = options->Get(NanNew<String>("overshootDeringing"))->BooleanValue();
|
||||
baton->optimiseScans = options->Get(NanNew<String>("optimiseScans"))->BooleanValue();
|
||||
baton->withMetadata = options->Get(NanNew<String>("withMetadata"))->BooleanValue();
|
||||
baton->withMetadataOrientation = options->Get(NanNew<String>("withMetadataOrientation"))->Int32Value();
|
||||
// Output filename or __format for Buffer
|
||||
baton->output = *String::Utf8Value(options->Get(NanNew<String>("output"))->ToString());
|
||||
baton->tileSize = options->Get(NanNew<String>("tileSize"))->Int32Value();
|
||||
|
||||
Reference in New Issue
Block a user