Clean up CLI

This commit is contained in:
augustin64 2025-04-01 18:06:05 +02:00
parent d5ea644f76
commit 1d2a139d4c

View File

@ -12,10 +12,11 @@
#include <SimpleProgressBar.hpp> #include <SimpleProgressBar.hpp>
#include <stb_image_write.h> #include <stb_image_write.h>
// Global flag to silent verbose messages // Global flags
bool silent; bool silent = false;
bool test_energy; bool test_energy = false;
bool energy_recompute_all = false; bool energy_recompute_all = false;
int max_step = 1;
// Get index for any table indexed by [width*(i : height) + (j : width)], but a // Get index for any table indexed by [width*(i : height) + (j : width)], but a
// : dim_long, b : dim_large // : dim_long, b : dim_large
@ -81,7 +82,7 @@ std::vector<float> energy_e1(std::vector<unsigned char> source, int width,
} }
std::vector<int> optimal_seam(std::vector<float> energy, int width, int height, std::vector<int> optimal_seam(std::vector<float> energy, int width, int height,
bool vertical, int max_step = 1) { bool vertical) {
/** Given the energy value, returns the optimal seam */ /** Given the energy value, returns the optimal seam */
// dyn_energy is indexed by [dim_large*(i : dim_long) + (j : dim_large)] // dyn_energy is indexed by [dim_large*(i : dim_long) + (j : dim_large)]
@ -195,11 +196,11 @@ std::vector<int> carving_step(const std::vector<unsigned char> source_img,
std::vector<unsigned char> &output_img, std::vector<unsigned char> &output_img,
std::vector<float> &output_energy, int width, std::vector<float> &output_energy, int width,
int height, int nbChannels, int nbColorChannels, int height, int nbChannels, int nbColorChannels,
bool vertical, int max_step=1) { bool vertical) {
/** Carves an image and its energy by one seam, and recomputes the energy. /** Carves an image and its energy by one seam, and recomputes the energy.
Returns the optimal seam used */ Returns the optimal seam used */
std::vector<int> opt_seam = std::vector<int> opt_seam =
optimal_seam(source_energy, width, height, vertical,max_step=max_step); optimal_seam(source_energy, width, height, vertical);
remove_seam(source_img, output_img, width, height, nbChannels, vertical, remove_seam(source_img, output_img, width, height, nbChannels, vertical,
opt_seam); opt_seam);
@ -241,8 +242,7 @@ std::vector<int> carving_step(const std::vector<unsigned char> source_img,
} }
void seam_carving(unsigned char *source, int width, int height, int nbChannels, void seam_carving(unsigned char *source, int width, int height, int nbChannels,
const char *out_filename, int nbSeams, bool vertical, const char *out_filename, int nbSeams, bool vertical) {
bool test_energy = false, int max_step = 1) {
int nbColorChannels = nbChannels > 3 ? 3 : nbChannels; int nbColorChannels = nbChannels > 3 ? 3 : nbChannels;
int curWidth = width; int curWidth = width;
int curHeight = height; int curHeight = height;
@ -282,7 +282,7 @@ void seam_carving(unsigned char *source, int width, int height, int nbChannels,
float max_energy = __FLT_MIN__; float max_energy = __FLT_MIN__;
for (auto k = 0; k < width * height; k++) { for (auto k = 0; k < width * height; k++) {
max_energy = fmax(max_energy, ini_energy[k]); max_energy = std::max(max_energy, ini_energy[k]);
} }
if (max_energy != 0) { if (max_energy != 0) {
for (auto k = 0; k < width * height; k++) { for (auto k = 0; k < width * height; k++) {
@ -307,7 +307,7 @@ void seam_carving(unsigned char *source, int width, int height, int nbChannels,
for (auto seam_index = 0; seam_index < nbSeams; seam_index++) { for (auto seam_index = 0; seam_index < nbSeams; seam_index++) {
std::vector<int> opt_seam = carving_step( std::vector<int> opt_seam = carving_step(
source_img, source_energy, output_img, output_energy, curWidth, source_img, source_energy, output_img, output_energy, curWidth,
curHeight, nbChannels, nbColorChannels, vertical, max_step=max_step); curHeight, nbChannels, nbColorChannels, vertical);
std::copy(output_img.begin(), output_img.end(), source_img.begin()); std::copy(output_img.begin(), output_img.end(), source_img.begin());
std::copy(output_energy.begin(), output_energy.end(), std::copy(output_energy.begin(), output_energy.end(),
source_energy.begin()); source_energy.begin());
@ -348,22 +348,26 @@ void seam_carving(unsigned char *source, int width, int height, int nbChannels,
int main(int argc, char **argv) { int main(int argc, char **argv) {
CLI::App app{"seam-carving"}; CLI::App app{"seam-carving"};
std::string sourceImage; std::string sourceImage;
std::string maskImage = "mask.png";
std::string outputImage = "output.png";
int nbSeams = 1;
bool vertical = false;
app.add_option("-s,--source", sourceImage, "Source image") app.add_option("-s,--source", sourceImage, "Source image")
->required() ->required()
->check(CLI::ExistingFile); ->check(CLI::ExistingFile);
;
std::string outputImage = "output.png";
app.add_option("-o,--output", outputImage, "Output image")->required(); app.add_option("-o,--output", outputImage, "Output image")->required();
int nbSeams = 1; app.add_option("-m,--mask", maskImage, "Source image")
app.add_option("-n,--nb-seams", nbSeams, "Number of seams"); ->check(CLI::ExistingFile);
int max_step = 1;
app.add_option("--max-step", max_step, "Max width of step to find a seam"); app.add_option("-n,--nb-seams", nbSeams, "Number of seams")
bool vertical = false; ->check(CLI::Number);
app.add_option("--max-step", max_step, "Max width of step to find a seam")
->check(CLI::Number);
app.add_flag("--vertical", vertical, app.add_flag("--vertical", vertical,
"Vertical carving (remove vertical seams)"); "Vertical carving (remove vertical seams)");
silent = false;
app.add_flag("--silent", silent, "No verbose messages"); app.add_flag("--silent", silent, "No verbose messages");
test_energy = false;
app.add_flag("--test-energy", test_energy, app.add_flag("--test-energy", test_energy,
"Don't resize image, just try the specified energy function"); "Don't resize image, just try the specified energy function");
app.add_flag("--energy-recompute-all", energy_recompute_all, app.add_flag("--energy-recompute-all", energy_recompute_all,
@ -376,8 +380,8 @@ int main(int argc, char **argv) {
stbi_load(sourceImage.c_str(), &width, &height, &nbChannels, 0); stbi_load(sourceImage.c_str(), &width, &height, &nbChannels, 0);
nbSeams = std::min(nbSeams, width); nbSeams = std::min(nbSeams, width);
seam_carving(source, width, height, nbChannels, outputImage.c_str(), nbSeams, seam_carving(source, width, height, nbChannels, outputImage.c_str(),
vertical, test_energy = test_energy, max_step = max_step); nbSeams, vertical);
stbi_image_free(source); stbi_image_free(source);
exit(0); exit(0);