PintaProject / Pinta

Simple GTK# Paint Program
http://www.pinta-project.com/
MIT License
1.81k stars 275 forks source link

Rotating by fractional degrees #807

Closed logiclrd closed 4 months ago

logiclrd commented 4 months ago

Description Please support rotating by 1/10ths or 1/100ths of a degree.

Additional context For lining up multiple images to combine them into a larger image, very precise rotation is sometimes required. Could you enhance the Rotate/Zoom Layer function to support fractional degrees? I'm working on a set of scans right now where one of the parts is rotated slightly to the right with respect to the rest, but if I rotate it left by 1°, now it's slightly to the left with respect to the rest. It needs to be somewhere in between.

logiclrd commented 4 months ago

I decided to have a go at it and discovered two things:

1) HEAD is substantially different than the version in Snap :-P

2) The version of Gtk# that the version in Snap is using does not seem to expose the ability to have decimal digits in a SpinButton. But, the version HEAD is using should be able to do this using a method Configure, which exposes gtk_spin_button_configure.

I've never used Gtk before, but it looks like gtk_spin_button_configure can alter the configuration of a SpinButton so that its text input has decimal places without changing the step provided by the +/- buttons.

My first go at it looks like this:

index 8be5bc5d..1522c645 100644
--- a/Pinta.Gui.Widgets/Widgets/AnglePickerWidget.cs
+++ b/Pinta.Gui.Widgets/Widgets/AnglePickerWidget.cs
@@ -44,8 +44,8 @@ public sealed class AnglePickerWidget : Box
                hbox2.Append (anglepickergraphic1);

                spin = SpinButton.NewWithRange (0, 360, 1);
+               spin.Configure(spin.GetAdjustment(), 1, 2);
                spin.CanFocus = true;
-               spin.ClimbRate = 1;
                spin.Numeric = true;
                spin.Adjustment!.PageIncrement = 10;
                spin.Valign = Align.Start;

This compiles, but when I try to run the resulting build output, I get an error. Actually, I get an error trying to display an error:

Unhandled exception. System.NullReferenceException: Object reference not set to an instance of an object.
   at Pinta.Core.ChromeManager.ShowErrorDialog(Window parent, String message, String body, String details) in /code/Pinta/Pinta.Core/Managers/ChromeManager.cs:line 161
   at Pinta.MainClass.OnUnhandledException(Exception e) in /code/Pinta/Pinta/Main.cs:line 141
   at GLib.UnhandledException.Raise(Exception e)
   at GObject.Closure.InternalCallback(IntPtr closure, IntPtr returnValuePtr, UInt32 nParamValues, IntPtr paramValuesData, IntPtr invocationHint, IntPtr userData)

The actual error is this:

---
ERROR: Unhandled exception
---
Unable to find an entry point named 'adw_toolbar_view_new' in shared library 'Adw'.
---
System.EntryPointNotFoundException: Unable to find an entry point named 'adw_toolbar_view_new' in shared library 'Adw'.
   at Adw.Internal.ToolbarView.New()
   at Adw.ToolbarView.New()
   at Pinta.WindowShell..ctor(Application app, String name, String title, Int32 width, Int32 height, Boolean maximize) in /code/Pinta/Pinta/WindowShell.cs:line 42
   at Pinta.MainWindow.CreateWindow() in /code/Pinta/Pinta/MainWindow.cs:line 284
   at Pinta.MainWindow.Activate() in /code/Pinta/Pinta/MainWindow.cs:line 64
   at Pinta.MainClass.<>c__DisplayClass1_0.<OpenMainWindow>b__0(Application _, EventArgs _) in /code/Pinta/Pinta/Main.cs:line 102
   at GObject.Signal`1.<>c__DisplayClass11_0.<Connect>b__0(Value returnValue, Value[] parameters)
   at GObject.Closure.InternalCallback(IntPtr closure, IntPtr returnValuePtr, UInt32 nParamValues, IntPtr paramValuesData, IntPtr invocationHint, IntPtr userData)
---

I have never played with these things before and have no idea what the likely culprit is. :-(

JGCarroll commented 4 months ago

Is there a chance you're running on Ubuntu 22.04? The new Pinta would build there but won't run because the libraries are incompatible.

If so, you'd be better off either upgrading to Ubuntu 24.04 or potentially building your modifications via Snap itself, it's build files are here: https://github.com/jgcarroll/pinta-snap

You'd be able to just get away with replacing

source: https://github.com/pintaproject/pinta.git
    source-commit: 79f2799cba3a1a78c20ecbabfb6575204036f6c8 # 2.1.2 tag

To point to your repo

(And you'd maybe want to change the version field, or the Snap would claim to be 2.1.2 despite being on the significantly different version you're seeing.)

Building Snaps is really easy, on a native machine it's

sudo snap install snapcraft --classic
sudo snap install lxd
sudo snap lxd init --auto

At this point you might need to add your user to the lxd group:

sudo adduser $USER lxd

This would also need you to reboot the computer to have a full effect.

Cloning the repo:

git clone https://github.com/jgcarroll/pinta-snap

Building:

cd pinta-snap
snapcraft

Installing

sudo snap install pinta_release.snap --dangerous

Clean building

snapcraft clean
snapcraft

Running

pinta
logiclrd commented 4 months ago

Thanks so much for the detailed reply :-) I managed to upgrade to 24.04, and now it runs without issues. I'm not sure I'm a fan of the reorganization of Pinta's menu bar :-P Is that configurable??

In any case, my change appears to have worked so I'll fork the repo and set up a PR. :-)

logiclrd commented 4 months ago

This issue is resolved by #811.