26#include <hugin_config.h>
34#include <vigra/error.hxx>
48static void usage(
const char* name)
50 std::cout << name <<
": stitch a panorama image" << std::endl
54 <<
" It uses the transform function from PanoTools, the stitching itself" << std::endl
55 <<
" is quite simple, no seam feathering is done." << std::endl
56 <<
" only the non-antialiasing interpolators of panotools are supported" << std::endl
58 <<
" The following output formats (n option of panotools p script line)" << std::endl
59 <<
" are supported:"<< std::endl
61 <<
" JPEG, TIFF, PNG : Single image formats with internal blender"<< std::endl
62 <<
" JPEG_m, TIFF_m, PNG_m : multiple image files"<< std::endl
63 <<
" TIFF_multilayer : Multilayer tiff files, readable by The Gimp 2.0" << std::endl
65 <<
"Usage: " << name <<
" [options] -o output project_file (image files)" << std::endl
66 <<
" Options: " << std::endl
67 <<
" -c create coordinate images (only TIFF_m output)" << std::endl
68 <<
" -v|--verbose verbose output" << std::endl
69 <<
" -d|--debug print detailed output for gpu processing" << std::endl
70 <<
" -g|--gpu perform image remapping on the GPU" << std::endl
72 <<
" The following options can be used to override settings in the project file:" << std::endl
73 <<
" -i num remap only image with number num" << std::endl
74 <<
" (can be specified multiple times)" << std::endl
75 <<
" -m str set output file format (TIFF, TIFF_m, TIFF_multilayer," << std::endl
76 <<
" EXR, EXR_m, JPEG, JPEG_m, PNG, PNG_m)" << std::endl
77 <<
" -r ldr/hdr set output mode." << std::endl
78 <<
" ldr keep original bit depth and response" << std::endl
79 <<
" hdr merge to hdr" << std::endl
80 <<
" -e exposure set exposure for ldr mode" << std::endl
81 <<
" -p TYPE pixel type of the output. Can be one of:" << std::endl
82 <<
" UINT8 8 bit unsigned integer" << std::endl
83 <<
" UINT16 16 bit unsigned integer" << std::endl
84 <<
" INT16 16 bit signed integer" << std::endl
85 <<
" UINT32 32 bit unsigned integer" << std::endl
86 <<
" INT32 32 bit signed integer" << std::endl
87 <<
" FLOAT 32 bit floating point" << std::endl
88 <<
" -z|--compression set compression type." << std::endl
89 <<
" Possible options for tiff output:" << std::endl
90 <<
" NONE no compression" << std::endl
91 <<
" PACKBITS packbits compression" << std::endl
92 <<
" LZW lzw compression" << std::endl
93 <<
" DEFLATE deflate compression" << std::endl
94 <<
" For jpeg output set quality number" << std::endl
95 <<
" --bigtiff Use BigTIFF format for TIFF images" << std::endl
96 <<
" --ignore-exposure don't correct exposure" << std::endl
97 <<
" (this does not work with -e switch together)" << std::endl
98 <<
" --output-range-compression=value set range compression" << std::endl
99 <<
" value should be a real in range 0..20" << std::endl
100 <<
" --save-intermediate-images saves also the intermediate" << std::endl
101 <<
" images (only when output is TIFF, PNG or JPEG)" << std::endl
102 <<
" --intermediate-suffix=SUFFIX suffix for intermediate images" << std::endl
103 <<
" --final-suffix=SUFFIX suffix for the final image" << std::endl
104 <<
" --create-exposure-layers create all exposure layers" << std::endl
105 <<
" (this will always use TIFF)" << std::endl
106 <<
" --clip-exposure[=lower cutoff:upper cutoff]" << std::endl
107 <<
" mask automatically all dark and bright pixels" << std::endl
108 <<
" optionally you can specify the limits for the" << std::endl
109 <<
" lower and upper cutoff (specify in range 0...1," << std::endl
110 <<
" relative the full range)" << std::endl
111 <<
" --seam=hard|blend select the blend mode for the seam" << std::endl
119 const char*
optstring =
"z:cho:i:t:m:p:r:e:vgd";
124 std::string basename;
125 std::string outputFormat;
127 std::string compression;
135 std::string outputPixelType;
190 if (std::string(
optarg) ==
"ldr")
195 else if (std::string(
optarg) ==
"hdr")
250 <<
" \"" <<
tokens[1] <<
"\". This is no valid input." << std::endl;
259 <<
" Expected --clip-exposure=lower cutoff:upper cutoff" << std::endl
260 <<
" Both should be numbers between 0 and 1." << std::endl;
267 <<
" Expected --clip-exposure=lower cutoff:upper cutoff" << std::endl;
298 std::cout <<
"WARNING: Switch -t is deprecated. Set environment variable OMP_NUM_THREADS instead" << std::endl;
308#if defined __APPLE__ && defined __aarch64__
311 std::cout <<
"WARNING: GPU remapping is not supported on ARM Macs. Switching back to CPU remapping." << std::endl;
345 if (basename.empty())
372 std::cerr <<
"Incorrect number of images specified on command line\nProject required " << pano.
getNrOfImages() <<
" but " <<
nCmdLineImgs <<
" where given" << std::endl;
387 if (!outputFormat.empty())
389 std::cout <<
"Warning: Ignoring output format " << outputFormat << std::endl
390 <<
" Switch --create-exposure-layers will enforce TIFF_m output." << std::endl;
392 outputFormat =
"TIFF";
395 std::cout <<
"Warning: Ignoring specified output images." << std::endl
396 <<
" Switch --create-exposure-layers will always work on all active images." << std::endl;
400 if (outputFormat ==
"TIFF_m")
405 else if (outputFormat ==
"JPEG_m")
411 else if (outputFormat ==
"JPEG")
417 else if (outputFormat ==
"PNG_m")
423 else if (outputFormat ==
"PNG")
429 else if (outputFormat ==
"TIFF")
434 else if (outputFormat ==
"TIFF_multilayer")
439 else if (outputFormat ==
"EXR_m")
444 else if (outputFormat ==
"EXR")
449 else if (outputFormat !=
"")
451 std::cerr <<
"Error: unknown output format: " << outputFormat << endl;
455 if (!compression.empty())
465 int q =
atoi(compression.c_str());
466 if (
q > 0 &&
q <= 100)
472 std::cerr <<
"WARNING: \"" << compression <<
"\" is not valid compression value for jpeg images." << std::endl
473 <<
" Using value " << opts.
quality <<
" found in pto file." << std::endl;
479 if (!outputPixelType.empty())
495 std::cout <<
"WARNING: Switches --ignore-exposure and -e can't to used together." << std::endl
496 <<
" Ignore switch --ignore-exposure." << std::endl;
503 std::cout <<
"WARNING: Switch --ignore-exposure disables range compression." << std::endl
504 <<
" --output-range-compression is therefore ignored." << std::endl;
523 std::cerr <<
"The project file does not contains an image with number " << *
it << std::endl;
530 std::cout <<
"Project does not contain active images." << std::endl
531 <<
"Nothing to do for nona." << std::endl;
545 std::cout <<
"Nona-GPU does not support this projection. Switch to CPU calculation."<<std::endl;
572 std::cout <<
"Could not initialize GPU. Switching back to CPU calculation." << std::endl;
583 std::cerr <<
"ERROR: Could not determine exposure layers. Cancel execution." << std::endl;
597 std::ostringstream filename;
598 filename << basename << std::setfill(
'0') << std::setw(4) <<
i;
611 std::cout << std::endl;
625 catch (std::exception& e)
627 std::cerr <<
"caught exception: " << e.what() << std::endl;
declaration of functions to handle stacks and layers
Helper class for storing different options.
Dummy progress display, without output.
a progress display to print progress reports to a stream
This class will use the stitchPanorama function of nona.
virtual void run()
runs the algorithm.
PanoramaOptions::ProjectionFormat getProjection() const
double outputExposureValue
std::string tiffCompression
std::string outputPixelType
std::string outputImageType
double outputRangeCompression
const SrcPanoImage & getImage(std::size_t nr) const
get a panorama image, counting starts with 0
const PanoramaOptions & getOptions() const
returns the options for this panorama
bool ReadPTOFile(const std::string &filename, const std::string &prefix="")
read pto file from the given filename into Panorama object it does some checks on the file and issues...
void setImageFilename(unsigned int img, const std::string &fname)
set a new image filename
void setOptions(const PanoramaOptions &opt)
set new output settings This is not used directly for optimizing/stiching, but it can be feed into ru...
UIntSet getActiveImages() const
get active images
std::size_t getNrOfImages() const
number of images.
std::map< std::string, std::string > AdvancedOptions
void SetAdvancedOption(AdvancedOptions &opts, const std::string &name, const bool value)
store the option with name in AdvancedOptions
bool GetAdvancedOption(const AdvancedOptions &opts, const std::string &name, const bool defaultValue)
check if given option is saved and return its boolean value, otherwise return defaultValue
std::vector< UIntSet > UIntSetVector
UIntSet getImagesinROI(const PanoramaData &pano, const UIntSet activeImages)
returns set of images which are visible in output ROI
std::set< unsigned int > UIntSet
std::string toupper(const std::string &s)
std::vector< std::string > SplitString(const std::string &s, const std::string &sep)
split string s at given sep, returns vector of strings
bool initGPU(int *argcp, char **argv)
Try to initalise GLUT and GLEW, and create an OpenGL context for GPU stitching.
bool wrapupGPU()
cleanup GPU settings
std::string tolower(const std::string &s)
convert a string to lowercase
std::string GetHuginVersion()
return a string with version numbers
bool stringToDouble(const STR &str_, double &dest)
convert a string to a double, ignore localisation.
std::string stripPath(const std::string &filename)
remove the path of a filename (mainly useful for gui display of filenames)
std::string getPathPrefix(const std::string &filename)
Get the path to a filename.
void SetGPUDebugMessages(const bool doPrint)
int main(int argc, char *argv[])
bool set_contains(const _Container &c, const typename _Container::key_type &key)
std::vector< deghosting::BImagePtr > threshold(const std::vector< deghosting::FImagePtr > &inputImages, const double threshold, const uint16_t flags)
Threshold function used for creating alpha masks for images.