Merge branch '32b-tiff-output-cli' into dev (Fix #2357)

- Adds support of 16 bits float tiff images in GUI and command line
- Adds support of 32 bits float tiff images in command line
This commit is contained in:
Hombre
2018-08-31 22:13:37 +02:00
19 changed files with 253 additions and 135 deletions

View File

@@ -228,7 +228,7 @@ bool BatchQueue::saveBatchQueue ()
// The column's header is mandatory (the first line will be skipped when loaded)
file << "input image full path|param file full path|output image full path|file format|jpeg quality|jpeg subsampling|"
<< "png bit depth|png compression|tiff bit depth|uncompressed tiff|save output params|force format options|fast export|<end of line>"
<< "png bit depth|png compression|tiff bit depth|tiff is float|uncompressed tiff|save output params|force format options|fast export|<end of line>"
<< std::endl;
// method is already running with entryLock, so no need to lock again
@@ -246,7 +246,7 @@ bool BatchQueue::saveBatchQueue ()
#endif
<< saveFormat.jpegQuality << '|' << saveFormat.jpegSubSamp << '|'
<< saveFormat.pngBits << '|'
<< saveFormat.tiffBits << '|' << saveFormat.tiffUncompressed << '|'
<< saveFormat.tiffBits << '|' << (saveFormat.tiffFloat ? 1 : 0) << '|' << saveFormat.tiffUncompressed << '|'
<< saveFormat.saveParams << '|' << entry->forceFormatOpts << '|'
<< entry->fast_pipeline << '|'
<< std::endl;
@@ -311,6 +311,7 @@ bool BatchQueue::loadBatchQueue ()
const auto jpegSubSamp = nextIntOr (options.saveFormat.jpegSubSamp);
const auto pngBits = nextIntOr (options.saveFormat.pngBits);
const auto tiffBits = nextIntOr (options.saveFormat.tiffBits);
const auto tiffFloat = nextIntOr (options.saveFormat.tiffFloat);
const auto tiffUncompressed = nextIntOr (options.saveFormat.tiffUncompressed);
const auto saveParams = nextIntOr (options.saveFormat.saveParams);
const auto forceFormatOpts = nextIntOr (options.forceFormatOpts);
@@ -352,6 +353,7 @@ bool BatchQueue::loadBatchQueue ()
saveFormat.jpegSubSamp = jpegSubSamp;
saveFormat.pngBits = pngBits;
saveFormat.tiffBits = tiffBits;
saveFormat.tiffFloat = tiffFloat == 1;
saveFormat.tiffUncompressed = tiffUncompressed != 0;
saveFormat.saveParams = saveParams != 0;
entry->forceFormatOpts = forceFormatOpts != 0;
@@ -608,7 +610,7 @@ rtengine::ProcessingJob* BatchQueue::imageReady (rtengine::IImagefloat* img)
int err = 0;
if (saveFormat.format == "tif") {
err = img->saveAsTIFF (fname, saveFormat.tiffBits, saveFormat.tiffUncompressed);
err = img->saveAsTIFF (fname, saveFormat.tiffBits, saveFormat.tiffFloat, saveFormat.tiffUncompressed);
} else if (saveFormat.format == "png") {
err = img->saveAsPNG (fname, saveFormat.pngBits);
} else if (saveFormat.format == "jpg") {

View File

@@ -175,9 +175,10 @@ Glib::ustring BatchQueueEntry::getToolTip (int x, int y)
tooltip += Glib::ustring::compose("\n\n%1: %2", M("BATCHQUEUE_DESTFILENAME"), outFileName);
if (forceFormatOpts) {
tooltip += Glib::ustring::compose("\n\n%1: %2 (%3 bits)", M("SAVEDLG_FILEFORMAT"), saveFormat.format,
tooltip += Glib::ustring::compose("\n\n%1: %2 (%3-bits%4)", M("SAVEDLG_FILEFORMAT"), saveFormat.format,
saveFormat.format == "png" ? saveFormat.pngBits :
saveFormat.format == "tif" ? saveFormat.tiffBits : 8);
saveFormat.format == "tif" ? saveFormat.tiffBits : 8,
saveFormat.format == "tif" && saveFormat.tiffFloat ? M("SAVEDLG_FILEFORMAT_FLOAT") : "");
if (saveFormat.format == "jpg") {
tooltip += Glib::ustring::compose("\n%1: %2\n%3: %4",

View File

@@ -1776,7 +1776,7 @@ bool EditorPanel::idle_saveImage (ProgressConnector<rtengine::IImagefloat*> *pc,
img->setSaveProgressListener (parent->getProgressListener());
if (sf.format == "tif")
ld->startFunc (sigc::bind (sigc::mem_fun (img, &rtengine::IImagefloat::saveAsTIFF), fname, sf.tiffBits, sf.tiffUncompressed),
ld->startFunc (sigc::bind (sigc::mem_fun (img, &rtengine::IImagefloat::saveAsTIFF), fname, sf.tiffBits, sf.tiffFloat, sf.tiffUncompressed),
sigc::bind (sigc::mem_fun (*this, &EditorPanel::idle_imageSaved), ld, img, fname, sf, pparams));
else if (sf.format == "png")
ld->startFunc (sigc::bind (sigc::mem_fun (img, &rtengine::IImagefloat::saveAsPNG), fname, sf.pngBits),
@@ -1993,9 +1993,9 @@ bool EditorPanel::saveImmediately (const Glib::ustring &filename, const SaveForm
int err = 0;
if (gimpPlugin) {
err = img->saveAsTIFF (filename, 32, true);
err = img->saveAsTIFF (filename, 32, true, true);
} else if (sf.format == "tif") {
err = img->saveAsTIFF (filename, sf.tiffBits, sf.tiffUncompressed);
err = img->saveAsTIFF (filename, sf.tiffBits, sf.tiffFloat, sf.tiffUncompressed);
} else if (sf.format == "png") {
err = img->saveAsPNG (filename, sf.pngBits);
} else if (sf.format == "jpg") {
@@ -2051,6 +2051,7 @@ bool EditorPanel::idle_sendToGimp ( ProgressConnector<rtengine::IImagefloat*> *p
SaveFormat sf;
sf.format = "tif";
sf.tiffBits = 16;
sf.tiffFloat = false;
sf.tiffUncompressed = true;
sf.saveParams = true;
@@ -2071,7 +2072,7 @@ bool EditorPanel::idle_sendToGimp ( ProgressConnector<rtengine::IImagefloat*> *p
ProgressConnector<int> *ld = new ProgressConnector<int>();
img->setSaveProgressListener (parent->getProgressListener());
ld->startFunc (sigc::bind (sigc::mem_fun (img, &rtengine::IImagefloat::saveAsTIFF), fileName, sf.tiffBits, sf.tiffUncompressed),
ld->startFunc (sigc::bind (sigc::mem_fun (img, &rtengine::IImagefloat::saveAsTIFF), fileName, sf.tiffBits, sf.tiffFloat, sf.tiffUncompressed),
sigc::bind (sigc::mem_fun (*this, &EditorPanel::idle_sentToGimp), ld, img, fileName));
} else {
Glib::ustring msg_ = Glib::ustring ("<b> Error during image processing\n</b>");

View File

@@ -267,6 +267,7 @@ int processLineParams ( int argc, char **argv )
int compression = 92;
int subsampling = 3;
int bits = -1;
bool isFloat = false;
std::string outputType = "";
unsigned errors = 0;
@@ -391,12 +392,15 @@ int processLineParams ( int argc, char **argv )
case 'b':
bits = atoi (currParam.substr (2).c_str());
if (bits != 8 && bits != 16) {
std::cerr << "Error: specify -b8 for 8-bit or -b16 for 16-bit output." << std::endl;
if (bits != 8 && bits != 16 && bits != 32) {
std::cerr << "Error: specify -b8 for 8-bit/integer or -b16 for 16-bit/integer or -b16f for 16-bit/float or -b32 for 32-bit/float output." << std::endl;
deleteProcParams (processingParams);
return -3;
}
isFloat = (bits == 16 && currParam.length() == 3 && currParam.at(2) == 'f') || bits == 32;
printf("Float output detected (%d bits)!\n", bits);
break;
case 't':
@@ -550,8 +554,11 @@ int processLineParams ( int argc, char **argv )
std::cout << " Chroma halved horizontally." << std::endl;
std::cout << " 3 = Best quality: 1x1, 1x1, 1x1 (4:4:4)" << std::endl;
std::cout << " No chroma subsampling." << std::endl;
std::cout << " -b<8|16> Specify bit depth per channel (default value: 16 for TIFF, 8 for PNG)." << std::endl;
std::cout << " Only applies to TIFF and PNG output, JPEG is always 8." << std::endl;
std::cout << " -b<8|16|16f|32> Specify bit depth per channel (default value: 16 for TIFF, 8 for PNG and JPEG)." << std::endl;
std::cout << " 8 = 8 bits integer, applies to JPEG, PNG and TIFF" << std::endl;
std::cout << " 16 = 16 bits integer, applies to PNG and TIFF" << std::endl;
std::cout << " 16f = 16 bits float, applies to TIFF" << std::endl;
std::cout << " 32 = 32 bits float, applies to TIFF" << std::endl;
std::cout << " -t[z] Specify output to be TIFF." << std::endl;
std::cout << " Uncompressed by default, or deflate compression with 'z'." << std::endl;
std::cout << " -n Specify output to be compressed PNG." << std::endl;
@@ -779,7 +786,7 @@ int processLineParams ( int argc, char **argv )
if ( outputType == "jpg" ) {
errorCode = resultImage->saveAsJPEG ( outputFile, compression, subsampling );
} else if ( outputType == "tif" ) {
errorCode = resultImage->saveAsTIFF ( outputFile, bits, compression == 0 );
errorCode = resultImage->saveAsTIFF ( outputFile, bits, isFloat, compression == 0 );
} else if ( outputType == "png" ) {
errorCode = resultImage->saveAsPNG ( outputFile, bits );
} else {

View File

@@ -301,6 +301,7 @@ void Options::setDefaults()
saveFormat.jpegSubSamp = 2;
saveFormat.pngBits = 8;
saveFormat.tiffBits = 16;
saveFormat.tiffFloat = false;
saveFormat.tiffUncompressed = true;
saveFormat.saveParams = true;
@@ -309,6 +310,7 @@ void Options::setDefaults()
saveFormatBatch.jpegSubSamp = 2;
saveFormatBatch.pngBits = 8;
saveFormatBatch.tiffBits = 16;
saveFormatBatch.tiffFloat = false;
saveFormatBatch.tiffUncompressed = true;
saveFormatBatch.saveParams = true;
@@ -756,6 +758,10 @@ void Options::readFromFile(Glib::ustring fname)
saveFormat.tiffBits = keyFile.get_integer("Output", "TiffBps");
}
if (keyFile.has_key ("Output", "TiffFloat")) {
saveFormat.tiffFloat = keyFile.get_boolean ("Output", "TiffFloat");
}
if (keyFile.has_key("Output", "TiffUncompressed")) {
saveFormat.tiffUncompressed = keyFile.get_boolean("Output", "TiffUncompressed");
}
@@ -785,6 +791,10 @@ void Options::readFromFile(Glib::ustring fname)
saveFormatBatch.tiffBits = keyFile.get_integer("Output", "TiffBpsBatch");
}
if (keyFile.has_key ("Output", "TiffFloatBatch")) {
saveFormatBatch.tiffFloat = keyFile.get_boolean ("Output", "TiffFloatBatch");
}
if (keyFile.has_key("Output", "TiffUncompressedBatch")) {
saveFormatBatch.tiffUncompressed = keyFile.get_boolean("Output", "TiffUncompressedBatch");
}
@@ -1950,6 +1960,7 @@ void Options::saveToFile(Glib::ustring fname)
keyFile.set_integer("Output", "JpegSubSamp", saveFormat.jpegSubSamp);
keyFile.set_integer("Output", "PngBps", saveFormat.pngBits);
keyFile.set_integer("Output", "TiffBps", saveFormat.tiffBits);
keyFile.set_boolean("Output", "TiffFloat", saveFormat.tiffFloat);
keyFile.set_boolean("Output", "TiffUncompressed", saveFormat.tiffUncompressed);
keyFile.set_boolean("Output", "SaveProcParams", saveFormat.saveParams);
@@ -1958,6 +1969,7 @@ void Options::saveToFile(Glib::ustring fname)
keyFile.set_integer("Output", "JpegSubSampBatch", saveFormatBatch.jpegSubSamp);
keyFile.set_integer("Output", "PngBpsBatch", saveFormatBatch.pngBits);
keyFile.set_integer("Output", "TiffBpsBatch", saveFormatBatch.tiffBits);
keyFile.set_boolean("Output", "TiffFloatBatch", saveFormatBatch.tiffFloat);
keyFile.set_boolean("Output", "TiffUncompressedBatch", saveFormatBatch.tiffUncompressed);
keyFile.set_boolean("Output", "SaveProcParamsBatch", saveFormatBatch.saveParams);

View File

@@ -50,6 +50,7 @@ struct SaveFormat {
jpegQuality (90),
jpegSubSamp (2),
tiffBits (8),
tiffFloat(false),
tiffUncompressed (true),
saveParams (true)
{
@@ -60,6 +61,7 @@ struct SaveFormat {
int jpegQuality;
int jpegSubSamp; // 1=best compression, 3=best quality
int tiffBits;
bool tiffFloat;
bool tiffUncompressed;
bool saveParams;
};

View File

@@ -40,6 +40,7 @@ SaveFormatPanel::SaveFormatPanel () : listener (nullptr)
format->append ("JPEG (8-bit)");
format->append ("TIFF (8-bit)");
format->append ("TIFF (16-bit)");
format->append ("TIFF (16-bit float)");
format->append ("TIFF (32-bit float)");
format->append ("PNG (8-bit)");
format->append ("PNG (16-bit)");
@@ -48,8 +49,9 @@ SaveFormatPanel::SaveFormatPanel () : listener (nullptr)
fstr[1] = "tif";
fstr[2] = "tif";
fstr[3] = "tif";
fstr[4] = "png";
fstr[4] = "tif";
fstr[5] = "png";
fstr[6] = "png";
hb1->attach (*flab, 0, 0, 1, 1);
hb1->attach (*format, 1, 0, 1, 1);
@@ -123,10 +125,12 @@ void SaveFormatPanel::init (SaveFormat &sf)
if (sf.format == "jpg") {
format->set_active (0);
} else if (sf.format == "png" && sf.pngBits == 16) {
format->set_active (5);
format->set_active (6);
} else if (sf.format == "png" && sf.pngBits == 8) {
format->set_active (4);
format->set_active (5);
} else if (sf.format == "tif" && sf.tiffBits == 32) {
format->set_active (4);
} else if (sf.format == "tif" && sf.tiffBits == 16 && sf.tiffFloat) {
format->set_active (3);
} else if (sf.format == "tif" && sf.tiffBits == 16) {
format->set_active (2);
@@ -150,20 +154,22 @@ SaveFormat SaveFormatPanel::getFormat ()
int sel = format->get_active_row_number();
sf.format = fstr[sel];
if (sel == 5) {
if (sel == 6) {
sf.pngBits = 16;
} else {
sf.pngBits = 8;
}
if (sel == 2) {
if (sel == 2 || sel == 3) {
sf.tiffBits = 16;
} else if (sel == 3) {
} else if (sel == 4) {
sf.tiffBits = 32;
} else {
sf.tiffBits = 8;
}
sf.tiffFloat = sel == 4 || sel == 3;
sf.jpegQuality = (int) jpegQual->getValue ();
sf.jpegSubSamp = jpegSubSamp->get_active_row_number() + 1;
sf.tiffUncompressed = tiffUncompressed->get_active();

View File

@@ -44,7 +44,7 @@ protected:
Gtk::Grid* jpegOpts;
Gtk::Label* jpegSubSampLabel;
FormatChangeListener* listener;
Glib::ustring fstr[6];
Glib::ustring fstr[7];
Gtk::CheckButton* savesPP;