Commit 0fae76cfd7f7c2bf390bc7effb8119075b8fdaff

Authored by m-holger
1 parent 0f67d851

Refactor `QPDFJob`: move `selections` to `Inputs`, update related logic in `hand…

…lePageSpecs` and `new_selection`, and simplify page specification handling.
libqpdf/QPDFJob.cc
@@ -425,9 +425,7 @@ QPDFJob::createQPDF() @@ -425,9 +425,7 @@ QPDFJob::createQPDF()
425 pdf.updateFromJSON(m->update_from_json); 425 pdf.updateFromJSON(m->update_from_json);
426 } 426 }
427 427
428 - if (!m->selections.empty()) {  
429 - handlePageSpecs(pdf);  
430 - } 428 + handlePageSpecs(pdf);
431 if (!m->rotations.empty()) { 429 if (!m->rotations.empty()) {
432 handleRotations(pdf); 430 handleRotations(pdf);
433 } 431 }
@@ -2351,10 +2349,10 @@ QPDFJob::Input::initialize(Inputs& in, QPDF* a_qpdf) @@ -2351,10 +2349,10 @@ QPDFJob::Input::initialize(Inputs& in, QPDF* a_qpdf)
2351 } 2349 }
2352 2350
2353 void 2351 void
2354 -QPDFJob::new_selection( 2352 +QPDFJob::Inputs::new_selection(
2355 std::string const& filename, std::string const& password, std::string const& range) 2353 std::string const& filename, std::string const& password, std::string const& range)
2356 { 2354 {
2357 - m->selections.emplace_back(filename, password, range); 2355 + selections.emplace_back(filename, password, range);
2358 } 2356 }
2359 2357
2360 void 2358 void
@@ -2430,11 +2428,14 @@ QPDFJob::Inputs::clear() @@ -2430,11 +2428,14 @@ QPDFJob::Inputs::clear()
2430 void 2428 void
2431 QPDFJob::handlePageSpecs(QPDF& pdf) 2429 QPDFJob::handlePageSpecs(QPDF& pdf)
2432 { 2430 {
  2431 + if (m->inputs.selections.empty()) {
  2432 + return;
  2433 + }
2433 auto& main_input = m->inputs.files[m->infilename]; 2434 auto& main_input = m->inputs.files[m->infilename];
2434 main_input.initialize(m->inputs, &pdf); 2435 main_input.initialize(m->inputs, &pdf);
2435 2436
2436 // Handle "." as a shortcut for the input file. 2437 // Handle "." as a shortcut for the input file.
2437 - for (auto& selection: m->selections) { 2438 + for (auto& selection: m->inputs.selections) {
2438 if (selection.filename == ".") { 2439 if (selection.filename == ".") {
2439 selection.filename = m->infilename; 2440 selection.filename = m->infilename;
2440 } else { 2441 } else {
@@ -2452,7 +2453,7 @@ QPDFJob::handlePageSpecs(QPDF& pdf) @@ -2452,7 +2453,7 @@ QPDFJob::handlePageSpecs(QPDF& pdf)
2452 m->inputs.process_all(); 2453 m->inputs.process_all();
2453 2454
2454 std::map<unsigned long long, std::set<QPDFObjGen>> copied_pages; 2455 std::map<unsigned long long, std::set<QPDFObjGen>> copied_pages;
2455 - for (auto& selection: m->selections) { 2456 + for (auto& selection: m->inputs.selections) {
2456 // Read original pages from the PDF, and parse the page range associated with this 2457 // Read original pages from the PDF, and parse the page range associated with this
2457 // occurrence of the file. 2458 // occurrence of the file.
2458 auto const& input = m->inputs.files[selection.filename]; 2459 auto const& input = m->inputs.files[selection.filename];
@@ -2476,7 +2477,7 @@ QPDFJob::handlePageSpecs(QPDF&amp; pdf) @@ -2476,7 +2477,7 @@ QPDFJob::handlePageSpecs(QPDF&amp; pdf)
2476 } 2477 }
2477 2478
2478 auto n_collate = m->collate.size(); 2479 auto n_collate = m->collate.size();
2479 - auto n_specs = m->selections.size(); 2480 + auto n_specs = m->inputs.selections.size();
2480 if (!(n_collate == 0 || n_collate == 1 || n_collate == n_specs)) { 2481 if (!(n_collate == 0 || n_collate == 1 || n_collate == n_specs)) {
2481 usage( 2482 usage(
2482 "--pages: if --collate has more than one value, it must have one value per page " 2483 "--pages: if --collate has more than one value, it must have one value per page "
@@ -2497,7 +2498,7 @@ QPDFJob::handlePageSpecs(QPDF&amp; pdf) @@ -2497,7 +2498,7 @@ QPDFJob::handlePageSpecs(QPDF&amp; pdf)
2497 while (got_pages) { 2498 while (got_pages) {
2498 got_pages = false; 2499 got_pages = false;
2499 for (size_t i = 0; i < n_specs; ++i) { 2500 for (size_t i = 0; i < n_specs; ++i) {
2500 - auto& page_data = m->selections.at(i); 2501 + auto& page_data = m->inputs.selections.at(i);
2501 for (size_t j = 0; j < m->collate.at(i); ++j) { 2502 for (size_t j = 0; j < m->collate.at(i); ++j) {
2502 if (cur_page.at(i) + j < page_data.selected_pages.size()) { 2503 if (cur_page.at(i) + j < page_data.selected_pages.size()) {
2503 got_pages = true; 2504 got_pages = true;
@@ -2518,7 +2519,7 @@ QPDFJob::handlePageSpecs(QPDF&amp; pdf) @@ -2518,7 +2519,7 @@ QPDFJob::handlePageSpecs(QPDF&amp; pdf)
2518 int out_pageno = 0; 2519 int out_pageno = 0;
2519 auto& this_afdh = pdf.acroform(); 2520 auto& this_afdh = pdf.acroform();
2520 std::set<QPDFObjGen> referenced_fields; 2521 std::set<QPDFObjGen> referenced_fields;
2521 - for (auto& selection: new_specs.empty() ? m->selections : new_specs) { 2522 + for (auto& selection: new_specs.empty() ? m->inputs.selections : new_specs) {
2522 auto& input = m->inputs.files[selection.filename]; 2523 auto& input = m->inputs.files[selection.filename];
2523 if (input.cfis) { 2524 if (input.cfis) {
2524 input.cfis->stayOpen(true); 2525 input.cfis->stayOpen(true);
libqpdf/QPDFJob_config.cc
@@ -978,7 +978,7 @@ QPDFJob::PagesConfig::PagesConfig(Config* c) : @@ -978,7 +978,7 @@ QPDFJob::PagesConfig::PagesConfig(Config* c) :
978 std::shared_ptr<QPDFJob::PagesConfig> 978 std::shared_ptr<QPDFJob::PagesConfig>
979 QPDFJob::Config::pages() 979 QPDFJob::Config::pages()
980 { 980 {
981 - if (!o.m->selections.empty()) { 981 + if (!o.m->inputs.selections.empty()) {
982 usage("--pages may only be specified one time"); 982 usage("--pages may only be specified one time");
983 } 983 }
984 return std::shared_ptr<PagesConfig>(new PagesConfig(this)); 984 return std::shared_ptr<PagesConfig>(new PagesConfig(this));
@@ -987,7 +987,7 @@ QPDFJob::Config::pages() @@ -987,7 +987,7 @@ QPDFJob::Config::pages()
987 QPDFJob::Config* 987 QPDFJob::Config*
988 QPDFJob::PagesConfig::endPages() 988 QPDFJob::PagesConfig::endPages()
989 { 989 {
990 - auto n_specs = config->o.m->selections.size(); 990 + auto n_specs = config->o.m->inputs.selections.size();
991 if (n_specs == 0) { 991 if (n_specs == 0) {
992 usage("--pages: no page specifications given"); 992 usage("--pages: no page specifications given");
993 } 993 }
@@ -998,24 +998,24 @@ QPDFJob::PagesConfig* @@ -998,24 +998,24 @@ QPDFJob::PagesConfig*
998 QPDFJob::PagesConfig::pageSpec( 998 QPDFJob::PagesConfig::pageSpec(
999 std::string const& filename, std::string const& range, char const* password) 999 std::string const& filename, std::string const& range, char const* password)
1000 { 1000 {
1001 - config->o.new_selection(filename, {password ? password : ""}, range); 1001 + config->o.m->inputs.new_selection(filename, {password ? password : ""}, range);
1002 return this; 1002 return this;
1003 } 1003 }
1004 1004
1005 QPDFJob::PagesConfig* 1005 QPDFJob::PagesConfig*
1006 QPDFJob::PagesConfig::file(std::string const& arg) 1006 QPDFJob::PagesConfig::file(std::string const& arg)
1007 { 1007 {
1008 - config->o.new_selection(arg, {}, {}); 1008 + config->o.m->inputs.new_selection(arg, {}, {});
1009 return this; 1009 return this;
1010 } 1010 }
1011 1011
1012 QPDFJob::PagesConfig* 1012 QPDFJob::PagesConfig*
1013 QPDFJob::PagesConfig::range(std::string const& arg) 1013 QPDFJob::PagesConfig::range(std::string const& arg)
1014 { 1014 {
1015 - if (config->o.m->selections.empty()) { 1015 + if (config->o.m->inputs.selections.empty()) {
1016 usage("in --range must follow a file name"); 1016 usage("in --range must follow a file name");
1017 } 1017 }
1018 - auto& last = config->o.m->selections.back(); 1018 + auto& last = config->o.m->inputs.selections.back();
1019 if (!last.range.empty()) { 1019 if (!last.range.empty()) {
1020 usage("--range already specified for this file"); 1020 usage("--range already specified for this file");
1021 } 1021 }
@@ -1026,10 +1026,10 @@ QPDFJob::PagesConfig::range(std::string const&amp; arg) @@ -1026,10 +1026,10 @@ QPDFJob::PagesConfig::range(std::string const&amp; arg)
1026 QPDFJob::PagesConfig* 1026 QPDFJob::PagesConfig*
1027 QPDFJob::PagesConfig::password(std::string const& arg) 1027 QPDFJob::PagesConfig::password(std::string const& arg)
1028 { 1028 {
1029 - if (config->o.m->selections.empty()) { 1029 + if (config->o.m->inputs.selections.empty()) {
1030 usage("in --pages, --password must follow a file name"); 1030 usage("in --pages, --password must follow a file name");
1031 } 1031 }
1032 - auto& last = config->o.m->selections.back(); 1032 + auto& last = config->o.m->inputs.selections.back();
1033 if (!last.password.empty()) { 1033 if (!last.password.empty()) {
1034 usage("--password already specified for this file"); 1034 usage("--password already specified for this file");
1035 } 1035 }
libqpdf/qpdf/QPDFJob_private.hh
@@ -66,6 +66,9 @@ struct QPDFJob::Inputs @@ -66,6 +66,9 @@ struct QPDFJob::Inputs
66 // Destroy all owned QPDF objects. Return false if any of the QPDF objects recorded warnings. 66 // Destroy all owned QPDF objects. Return false if any of the QPDF objects recorded warnings.
67 bool clear(); 67 bool clear();
68 68
  69 + void new_selection(
  70 + std::string const& filename, std::string const& password, std::string const& range);
  71 +
69 std::string encryption_file; 72 std::string encryption_file;
70 std::string encryption_file_password; 73 std::string encryption_file_password;
71 bool keep_files_open{true}; 74 bool keep_files_open{true};
@@ -73,6 +76,7 @@ struct QPDFJob::Inputs @@ -73,6 +76,7 @@ struct QPDFJob::Inputs
73 size_t keep_files_open_threshold{DEFAULT_KEEP_FILES_OPEN_THRESHOLD}; 76 size_t keep_files_open_threshold{DEFAULT_KEEP_FILES_OPEN_THRESHOLD};
74 77
75 std::map<std::string, Input> files; 78 std::map<std::string, Input> files;
  79 + std::vector<Selection> selections;
76 80
77 private: 81 private:
78 QPDFJob& job; 82 QPDFJob& job;
@@ -263,7 +267,6 @@ class QPDFJob::Members @@ -263,7 +267,6 @@ class QPDFJob::Members
263 std::vector<UnderOverlay> overlay; 267 std::vector<UnderOverlay> overlay;
264 UnderOverlay* under_overlay{nullptr}; 268 UnderOverlay* under_overlay{nullptr};
265 Inputs inputs; 269 Inputs inputs;
266 - std::vector<Selection> selections;  
267 std::map<std::string, RotationSpec> rotations; 270 std::map<std::string, RotationSpec> rotations;
268 bool require_outfile{true}; 271 bool require_outfile{true};
269 bool replace_input{false}; 272 bool replace_input{false};