Browse Source

File chooser with proper extension

Getty Ritter 3 years ago
parent
commit
fa3fce93af
1 changed files with 52 additions and 11 deletions
  1. 52 11
      src/main.rs

+ 52 - 11
src/main.rs

@@ -1,6 +1,8 @@
 use anyhow::{anyhow, bail, Result};
+use gtk::prelude::WidgetExtManual;
 use gtk::{
-    BoxExt, ButtonExt, ContainerExt, EditableSignals, EntryExt, GtkWindowExt, LabelExt, WidgetExt,
+    BoxExt, ButtonExt, ContainerExt, DialogExt, EditableSignals, EntryExt, FileChooserExt,
+    GtkWindowExt, LabelExt, WidgetExt,
 };
 use std::cell::RefCell;
 use std::rc::Rc;
@@ -13,24 +15,30 @@ struct AppData {
 }
 
 impl AppData {
-    fn draw_to_file(&self) -> Result<()> {
-        let f = std::fs::File::create("samp.svg")?;
+    fn draw_to_file<P: AsRef<std::path::Path>>(&self, path: P) -> Result<()> {
+        let f = std::fs::File::create(path)?;
         let surf = cairo::SvgSurface::for_stream(100.0, 100.0, f)?;
-        self.render(&cairo::Context::new(&surf))?;
+        self.render(&cairo::Context::new(&surf), 100.0, 100.0)?;
         if let Err(err) = surf.finish_output_stream() {
             bail!(err.error);
         };
         Ok(())
     }
 
-    fn render(&self, ctx: &cairo::Context) -> Result<()> {
+    fn render(&self, ctx: &cairo::Context, w: f64, h: f64) -> Result<()> {
+        let off_x = (w - 100.) / 2.0;
+        let off_y = (h - 100.) / 2.0;
+
         let color = self.color();
         ctx.set_source_rgb(color.0, color.1, color.2);
         ctx.paint();
 
         ctx.set_source_rgb(0., 0., 0.);
+        ctx.rectangle(off_x, off_y, 100., 100.);
+        ctx.stroke();
+
+        ctx.move_to(off_x, off_y - 23.0);
 
-        ctx.move_to(0.0, -23.0);
         let layout = pangocairo::functions::create_layout(&ctx)
             .ok_or_else(|| anyhow!("Could not create layout"))?;
         layout.set_width(100 * 1024);
@@ -89,20 +97,24 @@ fn mk_app() {
 
     let container = gtk::Box::new(gtk::Orientation::Vertical, 2);
     let label = gtk::Label::new(None);
+    let button = gtk::Button::with_label("EXPORT IT");
 
     {
         let color = gtk::Entry::new();
         let app = app.clone();
         let window = window.clone();
         let label = label.clone();
+        let button = button.clone();
         color.connect_changed(move |s| {
             let str = s.get_text();
             if let Some(color) = dmc::LOOKUP.get(str.as_str()) {
                 app.data.borrow_mut().dmc = Some(*color.clone());
                 label.set_text(color.name);
+                button.set_sensitive(true);
             } else {
                 app.data.borrow_mut().dmc = None;
                 label.set_text("");
+                button.set_sensitive(false);
             }
             window.queue_draw_area(0, 0, 500, 200);
         });
@@ -110,11 +122,38 @@ fn mk_app() {
     }
 
     {
-        let button = gtk::Button::with_label("EXPORT IT");
+        button.set_sensitive(false);
         let app = app.clone();
+        let window = window.clone();
         button.connect_clicked(move |_| {
-            if let Err(err) = app.data.borrow_mut().draw_to_file() {
-                eprintln!("Error in rendering: {}", err);
+            let dialog = gtk::FileChooserDialog::with_buttons(
+                Some("Select filename"),
+                Some(&window),
+                gtk::FileChooserAction::Save,
+                &[
+                    ("_Cancel", gtk::ResponseType::Cancel),
+                    ("_Open", gtk::ResponseType::Ok),
+                ],
+            );
+            let filter = gtk::FileFilter::new();
+            filter.add_mime_type("image/svg+xml");
+            filter.add_pattern("*.svg");
+            filter.set_name(Some("SVG image"));
+            dialog.add_filter(&filter);
+            if dialog.run() == gtk::ResponseType::Ok {
+                if let Some(tgt) = dialog.get_filename() {
+                    let mut tgt = tgt.to_owned();
+                    if !tgt.ends_with(".svg") {
+                        tgt.set_extension("svg");
+                    }
+                    println!("saving to {:?}", tgt);
+                    if let Err(err) = app.data.borrow_mut().draw_to_file(tgt) {
+                        eprintln!("Error in rendering: {}", err);
+                    }
+                }
+            }
+            unsafe {
+                dialog.destroy();
             }
         });
         container.pack_start(&button, false, true, 0);
@@ -125,8 +164,10 @@ fn mk_app() {
 
     {
         let canvas = gtk::DrawingArea::new();
-        canvas.connect_draw(move |_cv, ctx| {
-            if let Err(err) = app.data.borrow_mut().render(ctx) {
+        canvas.connect_draw(move |cv, ctx| {
+            let w = cv.get_allocated_width();
+            let h = cv.get_allocated_height();
+            if let Err(err) = app.data.borrow_mut().render(ctx, w as f64, h as f64) {
                 eprintln!("Error in rendering: {}", err);
             }
             gtk::Inhibit(false)