How to remove transparency from a TIF and replace with white background
How to remove transparency from a TIF and replace with white background
Hello,
i've attached an example file. How can I remove the transparency from a TIF file with ImageMagick C-API?
I already tried to debug with VisualMagick's tool "UTIL_convert" (VisualDynamicMT) with the command line parameter "[TIF_File] [JPG_File]" and this works, but I can't find out why.
Please could someone help?
Best Regards
https://www.dropbox.com/s/6b9khjnh74iauph/test.tif?dl=0
i've attached an example file. How can I remove the transparency from a TIF file with ImageMagick C-API?
I already tried to debug with VisualMagick's tool "UTIL_convert" (VisualDynamicMT) with the command line parameter "[TIF_File] [JPG_File]" and this works, but I can't find out why.
Please could someone help?
Best Regards
https://www.dropbox.com/s/6b9khjnh74iauph/test.tif?dl=0
-
- Posts: 12159
- Joined: 2010-01-23T23:01:33-07:00
- Authentication code: 1151
- Location: England, UK
Re: How to remove transparency from a TIF and replace with white background
There are two APIs for C. Which one do you use?
What version of IM do you use?
What version of IM do you use?
snibgo's IM pages: im.snibgo.com
Re: How to remove transparency from a TIF and replace with white background
Hello,
Regards
I use ImageMagick 7.0.7-22 Q16 x64 on Windows 10
I don't know what you mean exactly, I use MagickCore and MagickWand. Hope this is what you expected.
Regards
-
- Posts: 12159
- Joined: 2010-01-23T23:01:33-07:00
- Authentication code: 1151
- Location: England, UK
Re: How to remove transparency from a TIF and replace with white background
The usual way of removing transparency is by flattening against a colour:
The MagickCore functions for this are:
Code: Select all
magick in.png -background blue -layers flatten out.png
Code: Select all
QueryColorCompliance ("blue", AllCompliance, &inImg->background_color, exception);
Image * outImg = MergeImageLayers(inImg, FlattenLayer, exception);
snibgo's IM pages: im.snibgo.com
Re: How to remove transparency from a TIF and replace with white background
But in my case I have already a transparent background and want this to be replaced with a white background.
The following code do not work:
Regards
The following code do not work:
Code: Select all
QueryColorCompliance ("white", AllCompliance, &inImg->background_color, exception);
Image * outImg = MergeImageLayers(inImg, FlattenLayer, exception);
-
- Posts: 12159
- Joined: 2010-01-23T23:01:33-07:00
- Authentication code: 1151
- Location: England, UK
Re: How to remove transparency from a TIF and replace with white background
It works fine for me. For you, does it compile? Does it run without error? How do you know it doesn't work?Roman80 wrote:The following code do not work:
snibgo's IM pages: im.snibgo.com
Re: How to remove transparency from a TIF and replace with white background
Hi,
i prepared a running example, which demonstrates that it is not working:
After compiling, run it like "[output-binary] test.tif test_out.tif"
This will generate a file called "test_out.tif" without the QueryColorCompliance() function called and a file called "test_out_2.tif" which should have the transparency background replaced with a white background.
But the two images are the same and both images have a transparent background
Regards
i prepared a running example, which demonstrates that it is not working:
Code: Select all
#include <memory>
#include <string>
#include <iostream>
#ifdef _WIN32
# pragma warning(disable : 5033) // warning C5033: 'register' is no longer a supported storage class
#endif
#include <MagickCore/MagickCore.h>
class MagickUse {
public:
MagickUse(char **argv) {
MagickCoreGenesis(*argv, MagickTrue);
}
~MagickUse() {
MagickCoreTerminus();
}
};
int main(int argc, char* argv[]) {
// Usage: prg [INPUT_FILE] [OUTPUT_FILE]
const std::string inputFile = argv[argc - 2];
const std::string outputFile = argv[argc - 1];
const std::string outputFile2 = [=] { // a lambda because we want a const variable
const size_t pos = outputFile.rfind('.');
std::string tmp(outputFile);
tmp.insert(pos, "_2");
return tmp;
}();
std::unique_ptr<MagickUse> magickUse(new MagickUse(argv));
std::shared_ptr<ExceptionInfo> exception(AcquireExceptionInfo(), DestroyExceptionInfo);
std::shared_ptr<ImageInfo> pImageInfoInput(CloneImageInfo((ImageInfo *)NULL), DestroyImageInfo);
strcpy(pImageInfoInput->filename, inputFile.c_str());
std::cout << "Input file: " << pImageInfoInput->filename << std::endl;
std::shared_ptr<Image> inputImage(ReadImage(pImageInfoInput.get(), exception.get()), DestroyImage);
if (exception->severity != UndefinedException)
CatchException(exception.get());
if (!inputImage)
return 1;
std::shared_ptr<ImageInfo> pImageInfoOutput(CloneImageInfo((ImageInfo *)NULL), DestroyImageInfo);
strcpy(pImageInfoOutput->filename, outputFile.c_str());
std::cout << "Output file (before changes): " << pImageInfoOutput->filename << std::endl;
MagickBooleanType retVal = WriteImages(pImageInfoOutput.get(), inputImage.get(), outputFile.c_str() , exception.get());
std::shared_ptr<ImageInfo> pImageInfoOutput2(CloneImageInfo((ImageInfo *)NULL), DestroyImageInfo);
strcpy(pImageInfoOutput2->filename, outputFile2.c_str());
std::cout << "Output file (after changes): " << pImageInfoOutput2->filename << std::endl;
QueryColorCompliance("white", AllCompliance, &inputImage->background_color, exception.get());
Image *outImg = MergeImageLayers(inputImage.get(), FlattenLayer, exception.get());
retVal = WriteImages(pImageInfoOutput2.get(), outImg, outputFile.c_str(), exception.get());
return 0;
}
This will generate a file called "test_out.tif" without the QueryColorCompliance() function called and a file called "test_out_2.tif" which should have the transparency background replaced with a white background.
But the two images are the same and both images have a transparent background
Regards
-
- Posts: 12159
- Joined: 2010-01-23T23:01:33-07:00
- Authentication code: 1151
- Location: England, UK
Re: How to remove transparency from a TIF and replace with white background
You asked for the functions in C-API. I gave you the ones for MagickCore, in the C language. Here's a sample progam that reads an input and writes an output flattened against any colour.
But your example program uses C++ (CPP). Sorry, I don't use CPP.
Your C++ program won't compile for me under Gnu CPP compiler. It says:
Code: Select all
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <MagickCore/MagickCore.h>
int main(int argc,char **argv)
{
if (argc != 4) {
(void) fprintf(stdout,"Usage: %s input output colour\n",argv[0]);
exit(0);
}
MagickCoreGenesis (*argv, MagickTrue);
ExceptionInfo *exception = AcquireExceptionInfo();
ImageInfo *image_info = CloneImageInfo(NULL);
strcpy (image_info->filename, argv[1]);
Image * image = ReadImage (image_info, exception);
if (exception->severity != UndefinedException)
CatchException(exception);
if (!image)
exit(1);
QueryColorCompliance (argv[3], AllCompliance, &image->background_color, exception);
if (exception->severity != UndefinedException)
CatchException(exception);
Image * ftImg = MergeImageLayers (image, FlattenLayer, exception);
if (!ftImg)
MagickError(exception->severity,exception->reason,exception->description);
strcpy(ftImg->filename,argv[2]);
WriteImage (image_info, ftImg, exception);
DestroyImage(ftImg);
DestroyImage(image);
image_info=DestroyImageInfo(image_info);
exception=DestroyExceptionInfo(exception);
MagickCoreTerminus();
return(0);
}
Your C++ program won't compile for me under Gnu CPP compiler. It says:
Code: Select all
snibgo\flatc.cpp:36:56: error: 'strcpy' was not declared in this scope
snibgo's IM pages: im.snibgo.com
Re: How to remove transparency from a TIF and replace with white background
Please, add the additional header "#include <cstring>"Your C++ program won't compile for me under Gnu CPP compiler
I tried your example, but it gaves me the same result:
I compiled it and run it "[output-binary] test.tif test_out.tif white". The file "test.tif" and the file "test_out.tif" are the same and have both a transparent background.
To see the transparent background, open both files in Photoshop.
Regards
-
- Posts: 12159
- Joined: 2010-01-23T23:01:33-07:00
- Authentication code: 1151
- Location: England, UK
Re: How to remove transparency from a TIF and replace with white background
I added the include, and your CPP program compiled and ran but did not make the second file. I added checks for retVal, but the problem seemed to be that the second WriteImages used outputFile.c_str() but needed outputFile2.c_str().
My version of your CPP progam, flatc.cpp, is now:
It works fine with IM v7.0.7-28.
toes_holed.png:
flatc_out.png
flatc_out_2.png
The second output is flattened against white.
If you don't get the same result, perhaps there was a bug in IM v7.0.7-22, and upgrading may help.
My version of your CPP progam, flatc.cpp, is now:
Code: Select all
#include <memory>
#include <string>
#include <cstring>
#include <iostream>
#ifdef _WIN32
# pragma warning(disable : 5033) // warning C5033: 'register' is no longer a supported storage class
#endif
#include <MagickCore/MagickCore.h>
class MagickUse {
public:
MagickUse(char **argv) {
MagickCoreGenesis(*argv, MagickTrue);
}
~MagickUse() {
MagickCoreTerminus();
}
};
int main(int argc, char* argv[]) {
// Usage: prg [INPUT_FILE] [OUTPUT_FILE]
const std::string inputFile = argv[argc - 2];
const std::string outputFile = argv[argc - 1];
const std::string outputFile2 = [=] { // a lambda because we want a const variable
const size_t pos = outputFile.rfind('.');
std::string tmp(outputFile);
tmp.insert(pos, "_2");
return tmp;
}();
std::unique_ptr<MagickUse> magickUse(new MagickUse(argv));
std::shared_ptr<ExceptionInfo> exception(AcquireExceptionInfo(), DestroyExceptionInfo);
std::shared_ptr<ImageInfo> pImageInfoInput(CloneImageInfo((ImageInfo *)NULL), DestroyImageInfo);
strcpy(pImageInfoInput->filename, inputFile.c_str());
std::cout << "Input file: " << pImageInfoInput->filename << std::endl;
std::shared_ptr<Image> inputImage(ReadImage(pImageInfoInput.get(), exception.get()), DestroyImage);
if (exception->severity != UndefinedException)
CatchException(exception.get());
if (!inputImage)
return 1;
std::shared_ptr<ImageInfo> pImageInfoOutput(CloneImageInfo((ImageInfo *)NULL), DestroyImageInfo);
strcpy(pImageInfoOutput->filename, outputFile.c_str());
std::cout << "Output file (before changes): " << pImageInfoOutput->filename << std::endl;
MagickBooleanType retVal = WriteImages(pImageInfoOutput.get(), inputImage.get(), outputFile.c_str() , exception.get());
if (!retVal) {
std::cout << "Failed to write " << pImageInfoOutput->filename << std::endl;
}
std::shared_ptr<ImageInfo> pImageInfoOutput2(CloneImageInfo((ImageInfo *)NULL), DestroyImageInfo);
strcpy(pImageInfoOutput2->filename, outputFile2.c_str());
std::cout << "Output file (after changes): " << pImageInfoOutput2->filename << std::endl;
QueryColorCompliance("white", AllCompliance, &inputImage->background_color, exception.get());
Image *outImg = MergeImageLayers(inputImage.get(), FlattenLayer, exception.get());
retVal = WriteImages(pImageInfoOutput2.get(), outImg, outputFile2.c_str(), exception.get());
if (!retVal) {
std::cout << "Failed to write " << pImageInfoOutput2->filename << std::endl;
}
return 0;
}
Code: Select all
flatc toes_holed.png flatc_out.png
flatc_out.png
flatc_out_2.png
The second output is flattened against white.
If you don't get the same result, perhaps there was a bug in IM v7.0.7-22, and upgrading may help.
snibgo's IM pages: im.snibgo.com
Re: How to remove transparency from a TIF and replace with white background
Thanks, but maybe the problem is handling a Photoshop generated TIF with transparency with IM?
Try the TIF file with a TIF file as output, and IMPORTANT: open the generated file with Photoshop
Regards
Try the TIF file with a TIF file as output, and IMPORTANT: open the generated file with Photoshop
Regards
-
- Posts: 12159
- Joined: 2010-01-23T23:01:33-07:00
- Authentication code: 1151
- Location: England, UK
Re: How to remove transparency from a TIF and replace with white background
Photoshop transparency is a different issue. I suggest you first get your program to work with PNG input and output. If it doesn't work with PNG, it won't work with TIFF.
After converting toes_holed.png to a tiff, the program can flatten it, writing to tiff outputs.
I don't use Photoshop. PS has a number of mechanisms for transparency. The tiff you linked to in the OP has no transparency according to ImageMagick, exiftool or Gimp.
After converting toes_holed.png to a tiff, the program can flatten it, writing to tiff outputs.
I don't use Photoshop. PS has a number of mechanisms for transparency. The tiff you linked to in the OP has no transparency according to ImageMagick, exiftool or Gimp.
snibgo's IM pages: im.snibgo.com
Re: How to remove transparency from a TIF and replace with white background
OK, sorry, maybe I did not exactly describe my problem
1.) I tried it with your and with the corrected version of my program: TIF to PNG works, TIF to JPG works.
Both (PNG and JPG) have a white background regardless of the third parameter. (e.g. If i try "blue" as the third parameter than the background is still white)
Maybe this is also an issue?
2.)
Best Regards
1.) I tried it with your and with the corrected version of my program: TIF to PNG works, TIF to JPG works.
Both (PNG and JPG) have a white background regardless of the third parameter. (e.g. If i try "blue" as the third parameter than the background is still white)
Maybe this is also an issue?
2.)
This is my main issue at the moment for TIF files. Here I only want to replace the transparent background from a Photoshop generated TIF with a white background, but that do not work.Photoshop transparency is a different issue
Best Regards
-
- Posts: 12159
- Joined: 2010-01-23T23:01:33-07:00
- Authentication code: 1151
- Location: England, UK
Re: How to remove transparency from a TIF and replace with white background
JPG can't record transparency, so a JPG image is always fully opaque.
The C program that I showed (flatcol.c) uses argv[3] as the colour:
flatcol_out.png is:
Hacking flat.cpp to use a third parameter:
So, your CPP program can flatten against any colour, using QueryColorCompliance() and MergeImageLayers().
I don't use Photoshop. Perhaps there is a setting to make it save to TIFF with an alpha channel.
The C program that I showed (flatcol.c) uses argv[3] as the colour:
Code: Select all
flatcol toes_holed.png flatcol_out.png Blue
Hacking flat.cpp to use a third parameter:
Code: Select all
#include <memory>
#include <string>
#include <cstring>
#include <iostream>
#ifdef _WIN32
# pragma warning(disable : 5033) // warning C5033: 'register' is no longer a supported storage class
#endif
#include <MagickCore/MagickCore.h>
class MagickUse {
public:
MagickUse(char **argv) {
MagickCoreGenesis(*argv, MagickTrue);
}
~MagickUse() {
MagickCoreTerminus();
}
};
int main(int argc, char* argv[]) {
// Usage: prg [INPUT_FILE] [OUTPUT_FILE]
const std::string inputFile = argv[argc - 3];
const std::string outputFile = argv[argc - 2];
const std::string flatcol = argv[argc - 1];
const std::string outputFile2 = [=] { // a lambda because we want a const variable
const size_t pos = outputFile.rfind('.');
std::string tmp(outputFile);
tmp.insert(pos, "_2");
return tmp;
}();
std::unique_ptr<MagickUse> magickUse(new MagickUse(argv));
std::shared_ptr<ExceptionInfo> exception(AcquireExceptionInfo(), DestroyExceptionInfo);
std::shared_ptr<ImageInfo> pImageInfoInput(CloneImageInfo((ImageInfo *)NULL), DestroyImageInfo);
strcpy(pImageInfoInput->filename, inputFile.c_str());
std::cout << "Input file: " << pImageInfoInput->filename << std::endl;
std::shared_ptr<Image> inputImage(ReadImage(pImageInfoInput.get(), exception.get()), DestroyImage);
if (exception->severity != UndefinedException)
CatchException(exception.get());
if (!inputImage)
return 1;
std::shared_ptr<ImageInfo> pImageInfoOutput(CloneImageInfo((ImageInfo *)NULL), DestroyImageInfo);
strcpy(pImageInfoOutput->filename, outputFile.c_str());
std::cout << "Output file (before changes): " << pImageInfoOutput->filename << std::endl;
MagickBooleanType retVal = WriteImages(pImageInfoOutput.get(), inputImage.get(), outputFile.c_str() , exception.get());
if (!retVal) {
std::cout << "Failed to write " << pImageInfoOutput->filename << std::endl;
}
std::shared_ptr<ImageInfo> pImageInfoOutput2(CloneImageInfo((ImageInfo *)NULL), DestroyImageInfo);
strcpy(pImageInfoOutput2->filename, outputFile2.c_str());
std::cout << "Output file (after changes): " << pImageInfoOutput2->filename << std::endl;
QueryColorCompliance(flatcol.c_str(), AllCompliance, &inputImage->background_color, exception.get());
Image *outImg = MergeImageLayers(inputImage.get(), FlattenLayer, exception.get());
retVal = WriteImages(pImageInfoOutput2.get(), outImg, outputFile2.c_str(), exception.get());
if (!retVal) {
std::cout << "Failed to write " << pImageInfoOutput2->filename << std::endl;
}
return 0;
}
Code: Select all
c:\cygwin64\home\Alan\ImageMagick-7.0.7-28\ImageMagick>%IM7DEV%flatc f:\web\im\t
oes_holed.png flatc_pink_out.png pink
So, your CPP program can flatten against any colour, using QueryColorCompliance() and MergeImageLayers().
I don't use Photoshop. Perhaps there is a setting to make it save to TIFF with an alpha channel.
snibgo's IM pages: im.snibgo.com
- fmw42
- Posts: 25562
- Joined: 2007-07-02T17:14:51-07:00
- Authentication code: 1152
- Location: Sunnyvale, California, USA
Re: How to remove transparency from a TIF and replace with white background
Your original test.tif file does indeed open in Photoshop with transparency. But none of my other tools such as Mac Preview and GraphicsConverter and GIMP show the transparency. Even EXIFTOOL shows
258 BitsPerSample : 8 8 8
So the transparency is there in some hidden way that only Photoshop can read, perhaps in the XMP profile.
258 BitsPerSample : 8 8 8
So the transparency is there in some hidden way that only Photoshop can read, perhaps in the XMP profile.