diff --git a/apps/ely-doc/src/output.rs b/apps/ely-doc/src/output.rs index fe9822b..5248766 100644 --- a/apps/ely-doc/src/output.rs +++ b/apps/ely-doc/src/output.rs @@ -81,10 +81,8 @@ impl Docs { let path = source.work.join("print.pdf"); let printing = path.clone(); return self.write_pdf(tab, path, pdf, cx, move |docs, written, cx| match written { - Ok(()) => ely_office::print_later(printing, cx, |docs, error, cx| { - docs.output_failed(&error, cx) - }), - Err(error) => docs.output_failed(&error.to_string(), cx), + Ok(()) => ely_office::print_later(printing, cx), + Err(error) => docs.print_failed(&error.to_string(), cx), }); } let Some(dir) = ely_office::folder(source) else { diff --git a/apps/ely-mark/src/export.rs b/apps/ely-mark/src/export.rs index edcd7c7..7b1d4b2 100644 --- a/apps/ely-mark/src/export.rs +++ b/apps/ely-mark/src/export.rs @@ -343,9 +343,7 @@ impl Desk { if !job.lost.whole() { self.warn_lost(&job.lost, None, cx); } - return ely_office::print_later(pdf, cx, |desk, why, cx| { - desk.exported(Err(io::Error::other(why)), cx) - }); + return ely_office::print_later(pdf, cx); }; // Never over the open file, not even through a link. let moved = not_open(self, &to) diff --git a/apps/ely-pdf/src/output.rs b/apps/ely-pdf/src/output.rs index 7b548d7..4bdb745 100644 --- a/apps/ely-pdf/src/output.rs +++ b/apps/ely-pdf/src/output.rs @@ -95,7 +95,7 @@ impl Viewer { id, move |worker, doc| worker.get()?.print_copy(*doc, &out), move |viewer, done, _, cx| match done { - Ok(()) => ely_office::print_later(printing, cx, |viewer, error, cx| viewer.panel_failed(&error, cx)), + Ok(()) => ely_office::print_later(printing, cx), Err(error) => viewer.failed(&error, cx), }, cx, diff --git a/apps/ely-show/src/output.rs b/apps/ely-show/src/output.rs index 89bd761..ae87b29 100644 --- a/apps/ely-show/src/output.rs +++ b/apps/ely-show/src/output.rs @@ -185,7 +185,7 @@ impl Deck { let path = work.join("print.pdf"); let printing = path.clone(); return self.write_pdf(&output, path, cx, move |_, cx| { - ely_office::print_later(printing, cx, |deck, error, cx| deck.output_failed(&error, cx)) + ely_office::print_later(printing, cx) }); } let Some(dir) = ely_office::folder(source) else { diff --git a/apps/ely-table/src/output.rs b/apps/ely-table/src/output.rs index 10782eb..876a8e7 100644 --- a/apps/ely-table/src/output.rs +++ b/apps/ely-table/src/output.rs @@ -144,10 +144,8 @@ impl Book { tab, move |worker, doc| doc.export_pdf(worker, &url, &WHOLE), move |book, written, _, cx| match written { - Ok(()) => ely_office::print_later(path, cx, |book, error, cx| { - book.output_failed(&error, cx) - }), - Err(error) => book.output_failed(&error.to_string(), cx), + Ok(()) => ely_office::print_later(path, cx), + Err(error) => book.print_failed(&error.to_string(), cx), }, cx, ); diff --git a/crates/ely-office/src/lib.rs b/crates/ely-office/src/lib.rs index 3e5c472..4a11f7f 100644 --- a/crates/ely-office/src/lib.rs +++ b/crates/ely-office/src/lib.rs @@ -242,11 +242,7 @@ pub fn in_window( } /// Opens the print panel after GPUI releases the app. -pub fn print_later( - pdf: std::path::PathBuf, - cx: &mut Context, - failed: impl FnOnce(&mut H, String, &mut Context) + 'static, -) { +pub fn print_later(pdf: std::path::PathBuf, cx: &mut Context) { // The panel's modal loop calls back into GPUI. cx.spawn(async move |this, cx| { let printed = ely_platform::print::print_pdf(&pdf); @@ -258,7 +254,7 @@ pub fn print_later( Ok(printed) => log::info!("office: print done, printed {printed}"), Err(error) => { if this - .update(cx, |host, cx| failed(host, error.to_string(), cx)) + .update(cx, |host, cx| host.print_failed(&error.to_string(), cx)) .is_err() { log::error!("office: printing failed after its window closed: {error}"); @@ -293,6 +289,11 @@ pub trait Tabs: Host { self.toast_unlogged(text, severity, cx); } + fn print_failed(&self, error: &str, cx: &mut App) { + let text = text(cx, "office.print.failed", &[("error", error)]); + self.toast(text, Severity::Danger, cx); + } + /// A success toast with a button that opens `path`. fn toast_output(&self, text: SharedString, path: std::path::PathBuf, cx: &mut App) { log::info!("{}: {text}", Self::KIND.app.slug()); diff --git a/crates/ely-ui/src/i18n/office.rs b/crates/ely-ui/src/i18n/office.rs index 9338398..a13e77a 100644 --- a/crates/ely-ui/src/i18n/office.rs +++ b/crates/ely-ui/src/i18n/office.rs @@ -16,6 +16,7 @@ pub(super) const EN: &[(&str, &str)] = &[ "A conversion writes a new file; pick another name", ), ("office.error.changed", "The document changed meanwhile; try again"), + ("office.print.failed", "Printing failed: {error}"), ("office.recovery.failed", "A recovery copy was not written: {error}"), ("office.recovery.off", "Recovery copies are off for this run: {error}"), ("office.recovery.lost", "{name} could not be recovered: {error}"), @@ -101,6 +102,7 @@ pub(super) const ZH_CN: &[(&str, &str)] = &[ ("office.error.conflict", "{name} 已在磁盘上改动,保存已停止"), ("office.error.convert", "格式转换要写成新文件,请换个名字"), ("office.error.changed", "文档在此间已改动,请重试"), + ("office.print.failed", "打印失败:{error}"), ("office.recovery.failed", "恢复副本未能写入:{error}"), ("office.recovery.off", "本次运行不写恢复副本:{error}"), ("office.recovery.lost", "{name} 未能恢复:{error}"), diff --git a/tasks/BUGS.md b/tasks/BUGS.md index 4ba0bd5..c4bc5aa 100644 --- a/tasks/BUGS.md +++ b/tasks/BUGS.md @@ -20,7 +20,7 @@ - [x] T-10 CSV 导入对话框开着时打开任何别的对话框,待导入的文件静默消失 — 被挤开的导入回到队头,已读完的保留列类型;R2 PASS - [x] T-11 对话框比其标签活得久:导出、定义名称、重命名不可见却“开着”,挡住导入;名称表的“转到”激活已关闭的标签 — 关标签时一并关掉其对话框与选项列表;R1 PASS - [x] T-12 打印区域是整列或整行时页面设置无法应用 — 打印区域可为整列、整行(每端至多一个 $);R2 PASS -- [ ] T-13 打印失败报成“导出失败”(非 macOS 必现) +- [x] T-13 打印失败报成“导出失败”(非 macOS 必现) — print_later 自己以“打印失败”报错,五个应用同;R1 PASS - [ ] T-14 导入扫描把整个文件的每个字段都建成字符串 - [ ] T-15 非 UTF-8 文本的默认编码跟系统区域而不是界面语言 - [ ] S-01 切换幻灯片后主画布不重画 diff --git a/tasks/reviews/T-13-r1.md b/tasks/reviews/T-13-r1.md new file mode 100644 index 0000000..7ef22e9 --- /dev/null +++ b/tasks/reviews/T-13-r1.md @@ -0,0 +1 @@ +PASS