mirror of
https://github.com/storytold/pdfcraft.git
synced 2026-11-10 21:11:52 +00:00
fix(print): address review feedback on paper detection and page setup
This commit is contained in:
1 parent
08ec9aa058
commit
022f89cb7d
4 files changed
+45
-13
No files matched your search
@@ -159,6 +159,8 @@ impl PdfCraftApp {
|
||||
.map(|(name, _)| name.as_str())
|
||||
.or_else(|| pdfcraft_engine::print::PAPERS.get(self.print_draft.paper).map(|(name, _)| *name))
|
||||
);
|
||||
let size = self.print_draft.paper_size();
|
||||
v["print_paper_size"] = serde_json::json!([size.0, size.1]);
|
||||
v.to_string()
|
||||
}
|
||||
|
||||
@@ -277,6 +279,13 @@ impl PdfCraftApp {
|
||||
self.print_draft.paper = paper;
|
||||
} else if let Some(paper) = pdfcraft_engine::print::PAPERS.iter().position(|(canonical, _)| *canonical == name) {
|
||||
self.print_draft.paper = paper;
|
||||
} else if let Some(size) = v.get("print_paper_size").and_then(|s| {
|
||||
let w = s.get(0)?.as_f64()?;
|
||||
let h = s.get(1)?.as_f64()?;
|
||||
if w >= 72.0 && h >= 72.0 && w.is_finite() && h.is_finite() { Some((w, h)) } else { None }
|
||||
}) {
|
||||
self.print_draft.papers.push((name.to_string(), size));
|
||||
self.print_draft.paper = self.print_draft.papers.len() - 1;
|
||||
}
|
||||
}
|
||||
if let Some(on) = v["highlight_fields"].as_bool() {
|
||||
|
||||
@@ -172,7 +172,7 @@ impl PdfCraftApp {
|
||||
..keep
|
||||
};
|
||||
self.print_draft.update_printer_papers();
|
||||
if !picked && self.print_draft.paper == 0 {
|
||||
if !picked && !self.print_draft.paper_overridden && self.print_draft.paper == 0 {
|
||||
self.print_draft.auto_select_default_paper();
|
||||
}
|
||||
self.dialog = Some(crate::Dialog::Print);
|
||||
@@ -318,7 +318,7 @@ impl PdfCraftApp {
|
||||
d.printer_picked = false;
|
||||
d.printer = default_printer(&printers);
|
||||
d.update_printer_papers();
|
||||
if d.paper == 0 {
|
||||
if !d.paper_overridden && d.paper == 0 {
|
||||
d.auto_select_default_paper();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -165,7 +165,9 @@ pub(crate) fn body(
|
||||
d.show_driver_options = false;
|
||||
d.driver_error = None;
|
||||
d.update_printer_papers();
|
||||
d.auto_select_default_paper();
|
||||
if !d.paper_overridden {
|
||||
d.auto_select_default_paper();
|
||||
}
|
||||
}
|
||||
ui.end_row();
|
||||
// The spooler answered with no printer at all (#160): say so, rather than
|
||||
@@ -223,9 +225,11 @@ pub(crate) fn body(
|
||||
let page_setup_tip = if spool::HAS_PRINTER_PREFERENCES {
|
||||
tl!("Opens the printer driver's page setup: paper size, orientation and source.")
|
||||
} else {
|
||||
tl!("The printer driver's page setup: paper size, orientation and source.")
|
||||
tl!("Page setup dialog is not available on this system.")
|
||||
};
|
||||
let page_setup = ui.add_enabled(d.printer.is_some() && !browser, egui::Button::new(tl!("Page Setup…"))).on_hover_text(page_setup_tip);
|
||||
let page_setup = ui
|
||||
.add_enabled(d.printer.is_some() && !browser && spool::HAS_PRINTER_PREFERENCES, egui::Button::new(tl!("Page Setup…")))
|
||||
.on_hover_text(page_setup_tip);
|
||||
if page_setup.clicked()
|
||||
&& let Some(p) = d.printer.clone()
|
||||
{
|
||||
@@ -238,6 +242,9 @@ pub(crate) fn body(
|
||||
}
|
||||
}
|
||||
});
|
||||
if d.paper != before {
|
||||
d.paper_overridden = true;
|
||||
}
|
||||
// Label stock gets the label layout (cut, turned upright, fitted).
|
||||
if d.paper != before && d.paper == print::LABEL_PAPER {
|
||||
d.paper_before_label = Some(before);
|
||||
|
||||
@@ -61,6 +61,8 @@ pub struct PrintDraft {
|
||||
pub paper: usize,
|
||||
/// The paper chosen before Label put label stock in, so leaving Label gives it back (#3564).
|
||||
pub paper_before_label: Option<usize>,
|
||||
/// Whether the user has explicitly chosen or overridden the paper size.
|
||||
pub paper_overridden: bool,
|
||||
/// The list of papers available for selection (standard PAPERS plus any detected from the driver).
|
||||
pub papers: Vec<(String, (f64, f64))>,
|
||||
/// The sheet shown in the preview (0-based).
|
||||
@@ -122,6 +124,7 @@ impl Default for PrintDraft {
|
||||
dpi: 300.0,
|
||||
paper: 0,
|
||||
paper_before_label: None,
|
||||
paper_overridden: false,
|
||||
papers: default_papers(),
|
||||
sheet: 0,
|
||||
current_page: 0,
|
||||
@@ -144,14 +147,17 @@ pub fn default_papers() -> Vec<(String, (f64, f64))> {
|
||||
}
|
||||
|
||||
impl PrintDraft {
|
||||
/// The display name of the currently selected paper.
|
||||
pub fn paper_name(&self) -> &str {
|
||||
self.papers.get(self.paper).map(|p| p.0.as_str()).or_else(|| PAPERS.get(self.paper).map(|p| p.0)).unwrap_or(PAPERS[0].0)
|
||||
}
|
||||
|
||||
/// The dimensions in points `(width, height)` of the currently selected paper.
|
||||
pub fn paper_size(&self) -> (f64, f64) {
|
||||
self.papers.get(self.paper).map(|p| p.1).or_else(|| PAPERS.get(self.paper).map(|p| p.1)).unwrap_or(PAPERS[0].1)
|
||||
}
|
||||
|
||||
/// Find the index of a paper in `self.papers` matching `size`, allowing for orientation.
|
||||
pub fn matching_paper(&self, size: (f64, f64)) -> Option<usize> {
|
||||
print::matching_paper(size).or_else(|| {
|
||||
self.papers.iter().position(|(_, p)| {
|
||||
@@ -160,17 +166,16 @@ impl PrintDraft {
|
||||
})
|
||||
}
|
||||
|
||||
/// Refresh `self.papers` with driver-reported media sizes, preserving the current selection.
|
||||
pub fn update_printer_papers(&mut self) {
|
||||
let mut papers = default_papers();
|
||||
if let Some(ref printer) = self.printer {
|
||||
let detected = spool::printer_papers(printer);
|
||||
for (name, size) in detected {
|
||||
let norm = (size.0.min(size.1), size.0.max(size.1));
|
||||
if !papers.iter().any(|(n, s)| {
|
||||
n.eq_ignore_ascii_case(&name) || {
|
||||
let s_norm = (s.0.min(s.1), s.0.max(s.1));
|
||||
(s_norm.0 - norm.0).abs() <= 0.5 && (s_norm.1 - norm.1).abs() <= 0.5
|
||||
}
|
||||
if !papers.iter().any(|(_, s)| {
|
||||
let s_norm = (s.0.min(s.1), s.0.max(s.1));
|
||||
(s_norm.0 - norm.0).abs() <= 0.5 && (s_norm.1 - norm.1).abs() <= 0.5
|
||||
}) {
|
||||
papers.push((name, size));
|
||||
}
|
||||
@@ -184,7 +189,8 @@ impl PrintDraft {
|
||||
} else if let Some(pos) = self.papers.iter().position(|(_, s)| (s.0 - current_size.0).abs() <= 0.5 && (s.1 - current_size.1).abs() <= 0.5) {
|
||||
self.paper = pos;
|
||||
} else {
|
||||
self.paper = self.paper.min(self.papers.len().saturating_sub(1));
|
||||
self.papers.push((current_name, current_size));
|
||||
self.paper = self.papers.len() - 1;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -199,16 +205,26 @@ impl PrintDraft {
|
||||
|
||||
/// Apply paper size and orientation chosen in printer properties or page setup.
|
||||
pub fn apply_driver_paper(&mut self, name: String, size: (f64, f64)) {
|
||||
if !(size.0 >= 72.0 && size.1 >= 72.0 && size.0.is_finite() && size.1.is_finite()) {
|
||||
return;
|
||||
}
|
||||
self.paper_overridden = true;
|
||||
if let Some(pos) = self.matching_paper(size) {
|
||||
self.paper = pos;
|
||||
} else if !name.is_empty() {
|
||||
if let Some(pos) = self.papers.iter().position(|(n, _)| n.eq_ignore_ascii_case(&name)) {
|
||||
let norm = (size.0.min(size.1), size.0.max(size.1));
|
||||
if let Some(pos) = self.papers.iter().position(|(n, s)| {
|
||||
n.eq_ignore_ascii_case(&name) && {
|
||||
let s_norm = (s.0.min(s.1), s.0.max(s.1));
|
||||
(s_norm.0 - norm.0).abs() <= 1.0 && (s_norm.1 - norm.1).abs() <= 1.0
|
||||
}
|
||||
}) {
|
||||
self.paper = pos;
|
||||
} else {
|
||||
self.papers.push((name, size));
|
||||
self.paper = self.papers.len() - 1;
|
||||
}
|
||||
} else if size.0 > 0.0 && size.1 > 0.0 {
|
||||
} else {
|
||||
let custom_name = format!("{:.1} x {:.1} pt", size.0, size.1);
|
||||
self.papers.push((custom_name, size));
|
||||
self.paper = self.papers.len() - 1;
|
||||
|
||||
Reference in new issue
Block a user