edit/crop: Apply crop via checkmark overlay
This commit is contained in:
parent
40d425ac80
commit
9a5170de34
6 changed files with 62 additions and 26 deletions
|
|
@ -46,3 +46,8 @@ lpcrop {
|
||||||
.discarded-area {
|
.discarded-area {
|
||||||
background: var(--discarded-background);
|
background: var(--discarded-background);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.apply-button {
|
||||||
|
margin-right: 12px;
|
||||||
|
margin-top: -6px;
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,2 @@
|
||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<svg xmlns="http://www.w3.org/2000/svg" height="16px" viewBox="0 0 16 16" width="16px"><path d="m 13.398438 2.011719 c -0.394532 0.027343 -0.765626 0.210937 -1.027344 0.507812 l -5.78125 6.609375 l -1.890625 -2.519531 c -0.496094 -0.664063 -1.4375 -0.796875 -2.101563 -0.300781 c -0.316406 0.238281 -0.527344 0.59375 -0.582031 0.988281 c -0.058594 0.394531 0.046875 0.796875 0.285156 1.113281 l 3 4 c 0.273438 0.359375 0.691407 0.582032 1.144531 0.597656 c 0.449219 0.015626 0.886719 -0.171874 1.183594 -0.511718 l 7 -8 c 0.542969 -0.625 0.480469 -1.570313 -0.140625 -2.117188 c -0.300781 -0.261718 -0.691406 -0.394531 -1.089843 -0.367187 z m 0 0" fill="#222222"/></svg>
|
||||||
|
After Width: | Height: | Size: 710 B |
|
|
@ -71,8 +71,6 @@ mod imp {
|
||||||
image: TemplateChild<LpImage>,
|
image: TemplateChild<LpImage>,
|
||||||
#[template_child]
|
#[template_child]
|
||||||
pub(super) selection: TemplateChild<LpEditCropSelection>,
|
pub(super) selection: TemplateChild<LpEditCropSelection>,
|
||||||
#[template_child]
|
|
||||||
pub apply_crop: TemplateChild<gtk::Button>,
|
|
||||||
|
|
||||||
#[property(get, set, builder(LpAspectRatio::default()))]
|
#[property(get, set, builder(LpAspectRatio::default()))]
|
||||||
aspect_ratio: Cell<LpAspectRatio>,
|
aspect_ratio: Cell<LpAspectRatio>,
|
||||||
|
|
@ -229,9 +227,6 @@ mod imp {
|
||||||
self.crop_area_image_coord.replace(crop_area_image_coord);
|
self.crop_area_image_coord.replace(crop_area_image_coord);
|
||||||
}
|
}
|
||||||
|
|
||||||
let apply_sensitive = self.cropped();
|
|
||||||
self.apply_crop.set_visible(apply_sensitive);
|
|
||||||
|
|
||||||
self.obj().notify_cropped();
|
self.obj().notify_cropped();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -323,18 +323,6 @@
|
||||||
<property name="crop">LpEditCrop</property>
|
<property name="crop">LpEditCrop</property>
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
<child type="overlay">
|
|
||||||
<object class="GtkButton" id="apply_crop">
|
|
||||||
<property name="label">Apply</property>
|
|
||||||
<property name="action-name">edit-crop.apply-crop</property>
|
|
||||||
<property name="halign">end</property>
|
|
||||||
<property name="valign">start</property>
|
|
||||||
<style>
|
|
||||||
<class name="osd" />
|
|
||||||
<class name="pill" />
|
|
||||||
</style>
|
|
||||||
</object>
|
|
||||||
</child>
|
|
||||||
</object>
|
</object>
|
||||||
</property>
|
</property>
|
||||||
</object>
|
</object>
|
||||||
|
|
|
||||||
|
|
@ -26,7 +26,7 @@ use adw::{glib, gtk};
|
||||||
|
|
||||||
use super::crop::{LpAspectRatio, LpEditCrop, LpOrientation};
|
use super::crop::{LpAspectRatio, LpEditCrop, LpOrientation};
|
||||||
|
|
||||||
const MIN_SELECTION_SIZE: f32 = 50.;
|
const MIN_SELECTION_SIZE: f32 = 80.;
|
||||||
|
|
||||||
#[derive(Debug, Clone, Copy)]
|
#[derive(Debug, Clone, Copy)]
|
||||||
struct InResize {
|
struct InResize {
|
||||||
|
|
@ -155,6 +155,9 @@ mod imp {
|
||||||
#[template_child]
|
#[template_child]
|
||||||
handle_bottom_left: TemplateChild<adw::Bin>,
|
handle_bottom_left: TemplateChild<adw::Bin>,
|
||||||
|
|
||||||
|
#[template_child]
|
||||||
|
apply_button: TemplateChild<gtk::Button>,
|
||||||
|
|
||||||
#[template_child]
|
#[template_child]
|
||||||
selection_move: TemplateChild<gtk::GestureDrag>,
|
selection_move: TemplateChild<gtk::GestureDrag>,
|
||||||
|
|
||||||
|
|
@ -226,6 +229,7 @@ mod imp {
|
||||||
}
|
}
|
||||||
|
|
||||||
self.selection.set_cursor_from_name(Some("move"));
|
self.selection.set_cursor_from_name(Some("move"));
|
||||||
|
self.apply_button.set_cursor_from_name(Some("default"));
|
||||||
|
|
||||||
obj.crop()
|
obj.crop()
|
||||||
.connect_aspect_ratio_notify(|x| x.selection().imp().on_aspect_ratio_changed());
|
.connect_aspect_ratio_notify(|x| x.selection().imp().on_aspect_ratio_changed());
|
||||||
|
|
@ -256,7 +260,7 @@ mod imp {
|
||||||
|
|
||||||
let crop_area = imp.crop_area();
|
let crop_area = imp.crop_area();
|
||||||
|
|
||||||
imp.selection_in_resize.set(Some(InResize {
|
imp.set_selection_in_resize(Some(InResize {
|
||||||
corner,
|
corner,
|
||||||
initial_selection: crop_area,
|
initial_selection: crop_area,
|
||||||
}));
|
}));
|
||||||
|
|
@ -264,7 +268,7 @@ mod imp {
|
||||||
gesture.set_state(gtk::EventSequenceState::Claimed);
|
gesture.set_state(gtk::EventSequenceState::Claimed);
|
||||||
|
|
||||||
let crop_area = imp.crop_area();
|
let crop_area = imp.crop_area();
|
||||||
imp.selection_in_move.set(Some(InMove {
|
imp.set_selection_in_move(Some(InMove {
|
||||||
initial_selection: crop_area,
|
initial_selection: crop_area,
|
||||||
}));
|
}));
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -315,8 +319,8 @@ mod imp {
|
||||||
#[weak]
|
#[weak]
|
||||||
obj,
|
obj,
|
||||||
move |_, _, _| {
|
move |_, _, _| {
|
||||||
obj.imp().selection_in_resize.set(None);
|
obj.imp().set_selection_in_resize(None);
|
||||||
obj.imp().selection_in_move.set(None);
|
obj.imp().set_selection_in_move(None);
|
||||||
}
|
}
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
@ -683,6 +687,7 @@ mod imp {
|
||||||
self.crop_x.set(x);
|
self.crop_x.set(x);
|
||||||
self.space_top_left.set_width_request(x.round() as i32);
|
self.space_top_left.set_width_request(x.round() as i32);
|
||||||
self.obj().notify_crop_x();
|
self.obj().notify_crop_x();
|
||||||
|
self.update_apply_crop_visibility();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Set y coordinate of crop selection rectangle origin
|
/// Set y coordinate of crop selection rectangle origin
|
||||||
|
|
@ -695,6 +700,7 @@ mod imp {
|
||||||
self.crop_y.set(y);
|
self.crop_y.set(y);
|
||||||
self.space_top_left.set_height_request(y.round() as i32);
|
self.space_top_left.set_height_request(y.round() as i32);
|
||||||
self.obj().notify_crop_y();
|
self.obj().notify_crop_y();
|
||||||
|
self.update_apply_crop_visibility();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Set width of crop selection rectangle
|
/// Set width of crop selection rectangle
|
||||||
|
|
@ -707,6 +713,7 @@ mod imp {
|
||||||
self.crop_width.set(width);
|
self.crop_width.set(width);
|
||||||
self.selection.set_width_request(width.round() as i32);
|
self.selection.set_width_request(width.round() as i32);
|
||||||
self.obj().notify_crop_width();
|
self.obj().notify_crop_width();
|
||||||
|
self.update_apply_crop_visibility();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Set height of crop selection rectangle
|
/// Set height of crop selection rectangle
|
||||||
|
|
@ -719,6 +726,7 @@ mod imp {
|
||||||
self.crop_height.set(height);
|
self.crop_height.set(height);
|
||||||
self.selection.set_height_request(height.round() as i32);
|
self.selection.set_height_request(height.round() as i32);
|
||||||
self.obj().notify_crop_height();
|
self.obj().notify_crop_height();
|
||||||
|
self.update_apply_crop_visibility();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Width of area in which the crop selection can exist
|
/// Width of area in which the crop selection can exist
|
||||||
|
|
@ -728,6 +736,7 @@ mod imp {
|
||||||
|
|
||||||
fn set_total_width(&self, width: i32) {
|
fn set_total_width(&self, width: i32) {
|
||||||
self.obj().set_width_request(width);
|
self.obj().set_width_request(width);
|
||||||
|
self.update_apply_crop_visibility();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Height of area in which the crop selection can exist
|
/// Height of area in which the crop selection can exist
|
||||||
|
|
@ -737,6 +746,7 @@ mod imp {
|
||||||
|
|
||||||
fn set_total_height(&self, width: i32) {
|
fn set_total_height(&self, width: i32) {
|
||||||
self.obj().set_height_request(width);
|
self.obj().set_height_request(width);
|
||||||
|
self.update_apply_crop_visibility();
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(super) fn aspect_ratio_animation(&self) -> &adw::TimedAnimation {
|
pub(super) fn aspect_ratio_animation(&self) -> &adw::TimedAnimation {
|
||||||
|
|
@ -751,6 +761,24 @@ mod imp {
|
||||||
.build()
|
.build()
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn set_selection_in_resize(&self, in_resize: Option<InResize>) {
|
||||||
|
self.selection_in_resize.replace(in_resize);
|
||||||
|
self.update_apply_crop_visibility();
|
||||||
|
}
|
||||||
|
|
||||||
|
fn set_selection_in_move(&self, in_move: Option<InMove>) {
|
||||||
|
self.selection_in_move.replace(in_move);
|
||||||
|
self.update_apply_crop_visibility();
|
||||||
|
}
|
||||||
|
|
||||||
|
fn update_apply_crop_visibility(&self) {
|
||||||
|
self.apply_button.set_visible(
|
||||||
|
self.obj().is_cropped()
|
||||||
|
&& !self.selection_in_resize.get().is_some()
|
||||||
|
&& !self.selection_in_move.get().is_some(),
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -128,7 +128,7 @@
|
||||||
<property name="hexpand">true</property>
|
<property name="hexpand">true</property>
|
||||||
<layout>
|
<layout>
|
||||||
<property name="row">0</property>
|
<property name="row">0</property>
|
||||||
<property name="column">1</property>
|
<property name="column">2</property>
|
||||||
</layout>
|
</layout>
|
||||||
<style>
|
<style>
|
||||||
<class name="handle" />
|
<class name="handle" />
|
||||||
|
|
@ -136,12 +136,30 @@
|
||||||
</style>
|
</style>
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkButton" id="apply_button">
|
||||||
|
<property name="hexpand">true</property>
|
||||||
|
<layout>
|
||||||
|
<property name="row">1</property>
|
||||||
|
<property name="column">2</property>
|
||||||
|
</layout>
|
||||||
|
<property name="action-name">edit-crop.apply-crop</property>
|
||||||
|
<property name="icon-name">apply-crop</property>
|
||||||
|
<property name="halign">end</property>
|
||||||
|
<property name="valign">start</property>
|
||||||
|
<style>
|
||||||
|
<class name="circular" />
|
||||||
|
<class name="osd" />
|
||||||
|
<class name="apply-button" />
|
||||||
|
</style>
|
||||||
|
</object>
|
||||||
|
</child>
|
||||||
<child>
|
<child>
|
||||||
<object class="AdwBin" id="handle_bottom_left">
|
<object class="AdwBin" id="handle_bottom_left">
|
||||||
<property name="valign">end</property>
|
<property name="valign">end</property>
|
||||||
<property name="vexpand">true</property>
|
<property name="vexpand">true</property>
|
||||||
<layout>
|
<layout>
|
||||||
<property name="row">1</property>
|
<property name="row">2</property>
|
||||||
<property name="column">0</property>
|
<property name="column">0</property>
|
||||||
</layout>
|
</layout>
|
||||||
<style>
|
<style>
|
||||||
|
|
@ -157,8 +175,8 @@
|
||||||
<property name="valign">end</property>
|
<property name="valign">end</property>
|
||||||
<property name="vexpand">true</property>
|
<property name="vexpand">true</property>
|
||||||
<layout>
|
<layout>
|
||||||
<property name="row">1</property>
|
<property name="row">2</property>
|
||||||
<property name="column">1</property>
|
<property name="column">2</property>
|
||||||
</layout>
|
</layout>
|
||||||
<style>
|
<style>
|
||||||
<class name="handle" />
|
<class name="handle" />
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue