fix: replace GTK4 ColorDialogButton popovers with custom GTK buttons that spawn full native ColorDialog windows to avoid unresizing popovers
This commit is contained in:
+60
-27
@@ -1,7 +1,7 @@
|
|||||||
use crate::composite_icon::CompositeIcon;
|
use crate::composite_icon::CompositeIcon;
|
||||||
use gtk::prelude::*;
|
use gtk::prelude::*;
|
||||||
use gtk::{
|
use gtk::{
|
||||||
Box as GtkBox, ColorDialog, ColorDialogButton, Label, Orientation, Picture, ScrolledWindow,
|
Box as GtkBox, ColorDialog, Label, Orientation, Picture, ScrolledWindow,
|
||||||
};
|
};
|
||||||
use std::cell::RefCell;
|
use std::cell::RefCell;
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
@@ -209,38 +209,71 @@ pub fn build_editor_page(
|
|||||||
label.set_xalign(0.0);
|
label.set_xalign(0.0);
|
||||||
|
|
||||||
let rgba = gtk::gdk::RGBA::parse(&hex).unwrap_or(gtk::gdk::RGBA::BLACK);
|
let rgba = gtk::gdk::RGBA::parse(&hex).unwrap_or(gtk::gdk::RGBA::BLACK);
|
||||||
let dialog = ColorDialog::builder().build();
|
let current_rgba = Rc::new(RefCell::new(rgba));
|
||||||
let button = ColorDialogButton::new(Some(dialog));
|
|
||||||
button.set_rgba(&rgba);
|
let drawing_area = gtk::DrawingArea::new();
|
||||||
|
drawing_area.set_size_request(40, 24);
|
||||||
|
{
|
||||||
|
let current_rgba = Rc::clone(¤t_rgba);
|
||||||
|
drawing_area.set_draw_func(move |_, cr, width, height| {
|
||||||
|
let c = current_rgba.borrow();
|
||||||
|
cr.set_source_rgba(c.red() as f64, c.green() as f64, c.blue() as f64, 1.0);
|
||||||
|
cr.rectangle(0.0, 0.0, width as f64, height as f64);
|
||||||
|
cr.fill().expect("fill");
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
let button = gtk::Button::builder()
|
||||||
|
.child(&drawing_area)
|
||||||
|
.build();
|
||||||
|
|
||||||
|
let dialog = ColorDialog::builder().title("Pick a Color").build();
|
||||||
|
|
||||||
{
|
{
|
||||||
let composite = Rc::clone(&composite);
|
let composite = Rc::clone(&composite);
|
||||||
let tag = tag.clone();
|
let tag = tag.clone();
|
||||||
let refresh_preview = refresh_preview.clone();
|
let refresh_preview = refresh_preview.clone();
|
||||||
button.connect_rgba_notify(move |btn| {
|
let current_rgba = Rc::clone(¤t_rgba);
|
||||||
let new_rgba = btn.rgba();
|
let drawing_area = drawing_area.clone();
|
||||||
let new_hex = format!(
|
|
||||||
"#{:02x}{:02x}{:02x}",
|
button.connect_clicked(move |btn| {
|
||||||
(new_rgba.red() * 255.0).round() as u8,
|
let dialog = dialog.clone();
|
||||||
(new_rgba.green() * 255.0).round() as u8,
|
let tag = tag.clone();
|
||||||
(new_rgba.blue() * 255.0).round() as u8,
|
let composite = Rc::clone(&composite);
|
||||||
);
|
let refresh_preview = refresh_preview.clone();
|
||||||
let changed = {
|
let current_rgba = Rc::clone(¤t_rgba);
|
||||||
let mut comp = composite.borrow_mut();
|
let drawing_area = drawing_area.clone();
|
||||||
let res;
|
let parent_window = btn.root().and_downcast::<gtk::Window>();
|
||||||
if is_emblem {
|
let initial_color = current_rgba.borrow().clone();
|
||||||
res = comp.emblem.as_mut().unwrap().update_color(&tag, &new_hex).unwrap_or(false);
|
|
||||||
} else {
|
dialog.choose_rgba(parent_window.as_ref(), Some(&initial_color), gtk::gio::Cancellable::NONE, move |res| {
|
||||||
res = comp.bg.update_color(&tag, &new_hex).unwrap_or(false);
|
if let Ok(new_rgba) = res {
|
||||||
|
let new_hex = format!(
|
||||||
|
"#{:02x}{:02x}{:02x}",
|
||||||
|
(new_rgba.red() * 255.0).round() as u8,
|
||||||
|
(new_rgba.green() * 255.0).round() as u8,
|
||||||
|
(new_rgba.blue() * 255.0).round() as u8,
|
||||||
|
);
|
||||||
|
let changed = {
|
||||||
|
let mut comp = composite.borrow_mut();
|
||||||
|
let res;
|
||||||
|
if is_emblem {
|
||||||
|
res = comp.emblem.as_mut().unwrap().update_color(&tag, &new_hex).unwrap_or(false);
|
||||||
|
} else {
|
||||||
|
res = comp.bg.update_color(&tag, &new_hex).unwrap_or(false);
|
||||||
|
}
|
||||||
|
if res {
|
||||||
|
comp.is_modified = true;
|
||||||
|
}
|
||||||
|
res
|
||||||
|
};
|
||||||
|
if changed {
|
||||||
|
*current_rgba.borrow_mut() = new_rgba;
|
||||||
|
drawing_area.queue_draw();
|
||||||
|
refresh_preview();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if res {
|
});
|
||||||
comp.is_modified = true;
|
|
||||||
}
|
|
||||||
res
|
|
||||||
};
|
|
||||||
if changed {
|
|
||||||
refresh_preview();
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user