Skip to content

Add the "align object" tool#961

Merged
cameronwhite merged 18 commits into
PintaProject:masterfrom
Matthieu-LAURENT39:align-object
Sep 7, 2024
Merged

Add the "align object" tool#961
cameronwhite merged 18 commits into
PintaProject:masterfrom
Matthieu-LAURENT39:align-object

Conversation

@Matthieu-LAURENT39
Copy link
Copy Markdown
Contributor

@Matthieu-LAURENT39 Matthieu-LAURENT39 commented Sep 1, 2024

This aims to add the feature discussed in #936 and #813

This is a pretty barebone implementation for now (especially UI-wise).

I'm still really new to C#, so i would appreciate any tips if i'm doing anything the wrong way ^^

@Matthieu-LAURENT39
Copy link
Copy Markdown
Contributor Author

Matthieu-LAURENT39 commented Sep 1, 2024

Right now i'm blocking on two things:

  • Where should the tool go? It's currently in "Adjustments", but this feels like a weird place to put it. Maybe a new "effects" category should be made?
  • I'm not too sure what the most intuitive behavior would be for this tool when using selections. Should it use the selection as the "object" to align? Use the selection as the bounding box for the alignment? And in the latter case, how do we deal with non-rectangular selections?

edit: actually, it's probably best to have two checkboxes, "Align inside selection only" and "Object from selection only".
This allows the user to do all possible combinations of ignoring selection, selecting a specific object and aligning it relative to the whole image, selecting a specific object and aligning it within the selection, aligning the whole image relative to the selection.
That last one does seem a little weird though, so maybe instead we could have a dropdown offering only the first 3 options.

@cameronwhite
Copy link
Copy Markdown
Member

Thanks for looking at this!

I think having either the option to align within the bounding box of the selection, or aligning the selection contents within the image, could be useful. Ignoring the selection seems like the user could just do that beforehand by deselecting?

With implementing this as an effect, I think you might run into challenges with modifying the whole image since the result of your effect will be masked by the selection afterwards (normally, effects are only applied to the selection's contents). So it might be easier to implement it more like the Auto Crop tool if you need a lot more flexibility, or we can figure out the right API for effects to indicate they need to modify the whole image.

@Matthieu-LAURENT39
Copy link
Copy Markdown
Contributor Author

Thanks for looking at this!

I think having either the option to align within the bounding box of the selection, or aligning the selection contents within the image, could be useful. Ignoring the selection seems like the user could just do that beforehand by deselecting?

With implementing this as an effect, I think you might run into challenges with modifying the whole image since the result of your effect will be masked by the selection afterwards (normally, effects are only applied to the selection's contents). So it might be easier to implement it more like the Auto Crop tool if you need a lot more flexibility, or we can figure out the right API for effects to indicate they need to modify the whole image.

Indeed, i ran into that exact problem of selection masking the effect a few hours ago 😅
I don't think a whole lot of flexibility is needed, an API allowing to just say we want to edit the whole image seems like it would suffice. And i do feel like "align object" fits better under the effects tab than the image tab.

On another note, when trying to implement the selection-related options, the only way i could find to access the selection was with the "rois" parameter, which seems to just be an array of rectangle, so i'm not too sure how to deal with things like a circular selection. Or does that array of rectangle already represent a circle?

@cameronwhite
Copy link
Copy Markdown
Member

Right now I don't think the document's actual selection is passed down through the effect's API (similarly, because the masking against the selection is done implicitly afterwards)
The rectangle list would be a single entry with the bounds of the selection if IsTileable is false, otherwise it'll be a list of smaller sub-regions to process in parallel

@Matthieu-LAURENT39
Copy link
Copy Markdown
Contributor Author

That's not too much of an issue for the "align within the selection" option (since we just use the bounds anyways), but it is an issue for the "align selection within the image" option.
That makes it 2 required change for that latter option, when the former should work right now without any API changes.

Maybe i should only implement "align within the selection" for now, and leave "align selection within the image" for a later PR?
Especially since the same effect can be achieved by just copying the selection to a new empty layer the using the align tool.

@cameronwhite
Copy link
Copy Markdown
Member

Yeah, that sounds like a good approach to take 👍

@Matthieu-LAURENT39
Copy link
Copy Markdown
Contributor Author

Matthieu-LAURENT39 commented Sep 2, 2024

Should be all good, adding support for selection was surprisingly easy
I was thinking, with #953 just getting merged, it seems we're going to have a few object-based effects. Maybe we could create a new "object" effect category and put those there?

@Matthieu-LAURENT39
Copy link
Copy Markdown
Contributor Author

went ahead with it for now, we can always revert the commit if you would rather have it somewhere else

Copy link
Copy Markdown
Member

@cameronwhite cameronwhite left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is looking great so far! I left a couple notes and suggestions in the comments.

  • The new Object category sounds good to me, and the Feather effect could also probably be shifted there
  • It would also be great to add a unit test for the effect. Similar to the note in #953, feel free to extend the TestEffect API if you need to use a different input image.

Comment thread Pinta.Effects/Effects/AlignObjectEffect.cs Outdated
Comment thread Pinta.Effects/Effects/AlignObjectEffect.cs Outdated
MarginBottom = 12
};

topLeft = CreateCheckButton ("Top Left", AlignPosition.TopLeft);
Copy link
Copy Markdown
Member

@cameronwhite cameronwhite Sep 4, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These strings labels would need to become e.g. Translations.GetString("Top Left") in order for translations to work

One other idea for the UI though would be to use the same alignment buttons as the Resize Canvas dialog - what do you think about that approach? It might be less cluttered if there are other options added in the future, e.g. aligning only horizontally or only vertically

resize_canvas

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Indeed, that was the approach i originally wanted to take, but i didn't know if we had icons we could use for it.
I switched to that, although the center icon isn't that fitting, it should probably be something like a dot / circle.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good! I think the remaining fix is just to use Translations.GetString() for all the tooltips so they are translatable

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

completely slipped my mind 😅
should be good now!

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I should have been more clear, sorry :)
Doing Translations.GetString (tooltip) isn't exactly right - the problem is that those tooltip strings won't be picked up automatically and added to the translation template (po/messages.pot) as strings that can be translated (https://github.com/PintaProject/Pinta/wiki/Translations)

So the approach is to explicitly do Translations.GetString("Top Left"), Translations.GetString("Top Center") so that those strings are automatically picked up for translations

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Makes sense, moved the GetString calls to use literals

@cameronwhite cameronwhite linked an issue Sep 4, 2024 that may be closed by this pull request
@Matthieu-LAURENT39
Copy link
Copy Markdown
Contributor Author

Matthieu-LAURENT39 commented Sep 4, 2024

Added tests and took the comments into account
Should i also move the feather effect into the object category? Or is that too out-of-scope for the PR?

@cameronwhite
Copy link
Copy Markdown
Member

Added tests and took the comments into account Should i also move the feather effect into the object category? Or is that too out-of-scope for the PR?

Thanks! Updating the feather effect category is fine to add into this PR since it's a trivial change

Copy link
Copy Markdown
Member

@cameronwhite cameronwhite left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good, thanks for your contribution!

@cameronwhite cameronwhite merged commit 23d11ec into PintaProject:master Sep 7, 2024
@IArnaut2
Copy link
Copy Markdown
Contributor

Aligning object to selection (as bounding box) is still not implemented.

2026-03-23.13-42-55.mp4

@Matthieu-LAURENT39
Copy link
Copy Markdown
Contributor Author

Aligning object to selection (as bounding box) is still not implemented.
2026-03-23.13-42-55.mp4

I believe what you're looking for is already implemented.
If you have an active selection, the algorithm will find the object in that selection, and then align it using the selection as bounding box.

In your video, the object is outside the selection, so it is ignored.
It's not really possible to move objects from outside the selection, since effects aren't allowed to edit the image outside of the current selection.

@IArnaut2
Copy link
Copy Markdown
Contributor

Aligning object to selection (as bounding box) is still not implemented.
2026-03-23.13-42-55.mp4

I believe what you're looking for is already implemented. If you have an active selection, the algorithm will find the object in that selection, and then align it using the selection as bounding box.

In your video, the object is outside the selection, so it is ignored. It's not really possible to move objects from outside the selection, since effects aren't allowed to edit the image outside of the current selection.

It should work even if the object is outside the selection too.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Object Align

3 participants