Bug 735906 - Transform tools give unexpected results when transforming...

...certain sets of linked layers

Fix this bug for flip, rotate and general transforms (not for move yet):

gimp_item_linked_flip,rotate,transform(): always transform the passed
item too (do not filter it out of the list of items), so these functions
do the entire job of transforming a linked group now. Transforming the
active item separately didn't work (and is not implementable) if both
a layer and its parent layer group were linked.

flip tool, transform tool, layer->transform callbacks: don't call
gimp_item_foo() *and* (if the item is linked) gimp_item_linked_foo().
Instead call gimp_item_linked_foo() if the item is linked, and
gimp_item_foo() otherwise.

This commit also kills the mis-feature of transforming the selected
pixels of the active layer, and then the linked items completely. We
now either only transform the selected area *or* the linked group.
This commit is contained in:
Michael Natterer
2015-06-25 12:25:41 +02:00
parent 3f88b40af1
commit 25a696c7f8
5 changed files with 90 additions and 71 deletions

View File

@ -355,18 +355,15 @@ drawable_flip_cmd_callback (GtkAction *action,
break;
}
if (gimp_item_get_linked (item))
gimp_image_undo_group_start (image, GIMP_UNDO_GROUP_TRANSFORM,
GIMP_ITEM_GET_CLASS (item)->flip_desc);
gimp_item_flip (item, context,
(GimpOrientationType) value, axis, FALSE);
if (gimp_item_get_linked (item))
{
gimp_item_linked_flip (item, context,
(GimpOrientationType) value, axis, FALSE);
gimp_image_undo_group_end (image);
}
else
{
gimp_item_flip (item, context,
(GimpOrientationType) value, axis, FALSE);
}
gimp_image_flush (image);
@ -394,21 +391,18 @@ drawable_rotate_cmd_callback (GtkAction *action,
center_x = ((gdouble) off_x + (gdouble) gimp_item_get_width (item) / 2.0);
center_y = ((gdouble) off_y + (gdouble) gimp_item_get_height (item) / 2.0);
if (gimp_item_get_linked (item))
gimp_image_undo_group_start (image, GIMP_UNDO_GROUP_TRANSFORM,
GIMP_ITEM_GET_CLASS (item)->rotate_desc);
if (GIMP_IS_CHANNEL (item))
clip_result = TRUE;
gimp_item_rotate (item, context, (GimpRotationType) value,
center_x, center_y, clip_result);
if (gimp_item_get_linked (item))
{
gimp_item_linked_rotate (item, context, (GimpRotationType) value,
center_x, center_y, FALSE);
gimp_image_undo_group_end (image);
}
else
{
gimp_item_rotate (item, context, (GimpRotationType) value,
center_x, center_y, clip_result);
}
gimp_image_flush (image);

View File

@ -25,11 +25,14 @@
#include "gimpcontext.h"
#include "gimpimage.h"
#include "gimpimage-item-list.h"
#include "gimpimage-undo.h"
#include "gimpitem.h"
#include "gimpitem-linked.h"
#include "gimplist.h"
#include "gimpprogress.h"
#include "gimp-intl.h"
/* public functions */
@ -102,23 +105,25 @@ gimp_item_linked_flip (GimpItem *item,
gdouble axis,
gboolean clip_result)
{
GList *list;
GimpImage *image;
GList *items;
g_return_if_fail (GIMP_IS_ITEM (item));
g_return_if_fail (GIMP_IS_CONTEXT (context));
g_return_if_fail (gimp_item_get_linked (item) == TRUE);
g_return_if_fail (gimp_item_is_attached (item));
list = gimp_image_item_list_get_list (gimp_item_get_image (item), item,
GIMP_ITEM_TYPE_ALL,
GIMP_ITEM_SET_LINKED);
image = gimp_item_get_image (item);
list = gimp_image_item_list_filter (item, list);
items = gimp_image_item_list_get_list (image, NULL,
GIMP_ITEM_TYPE_ALL,
GIMP_ITEM_SET_LINKED);
items = gimp_image_item_list_filter (NULL, items);
gimp_image_item_list_flip (gimp_item_get_image (item), list, context,
gimp_image_item_list_flip (image, items, context,
flip_type, axis, clip_result);
g_list_free (list);
g_list_free (items);
}
void
@ -129,35 +134,42 @@ gimp_item_linked_rotate (GimpItem *item,
gdouble center_y,
gboolean clip_result)
{
GList *list;
GimpImage *image;
GList *items;
GList *channels;
g_return_if_fail (GIMP_IS_ITEM (item));
g_return_if_fail (GIMP_IS_CONTEXT (context));
g_return_if_fail (gimp_item_get_linked (item) == TRUE);
g_return_if_fail (gimp_item_is_attached (item));
list = gimp_image_item_list_get_list (gimp_item_get_image (item), item,
GIMP_ITEM_TYPE_LAYERS |
GIMP_ITEM_TYPE_VECTORS,
GIMP_ITEM_SET_LINKED);
image = gimp_item_get_image (item);
list = gimp_image_item_list_filter (item, list);
items = gimp_image_item_list_get_list (image, NULL,
GIMP_ITEM_TYPE_LAYERS |
GIMP_ITEM_TYPE_VECTORS,
GIMP_ITEM_SET_LINKED);
items = gimp_image_item_list_filter (NULL, items);
gimp_image_item_list_rotate (gimp_item_get_image (item), list, context,
channels = gimp_image_item_list_get_list (image, NULL,
GIMP_ITEM_TYPE_CHANNELS,
GIMP_ITEM_SET_LINKED);
channels = gimp_image_item_list_filter (NULL, channels);
if (items && channels)
gimp_image_undo_group_start (image, GIMP_UNDO_GROUP_TRANSFORM,
C_("undo-type", "Rotate Items"));
gimp_image_item_list_rotate (image, items, context,
rotate_type, center_x, center_y, clip_result);
g_list_free (list);
list = gimp_image_item_list_get_list (gimp_item_get_image (item), item,
GIMP_ITEM_TYPE_CHANNELS,
GIMP_ITEM_SET_LINKED);
list = gimp_image_item_list_filter (item, list);
gimp_image_item_list_rotate (gimp_item_get_image (item), list, context,
gimp_image_item_list_rotate (image, channels, context,
rotate_type, center_x, center_y, TRUE);
g_list_free (list);
if (items && channels)
gimp_image_undo_group_end (image);
g_list_free (items);
g_list_free (channels);
}
void
@ -169,7 +181,8 @@ gimp_item_linked_transform (GimpItem *item,
GimpTransformResize clip_result,
GimpProgress *progress)
{
GList *list;
GimpImage *image;
GList *items;
g_return_if_fail (GIMP_IS_ITEM (item));
g_return_if_fail (GIMP_IS_CONTEXT (context));
@ -177,16 +190,18 @@ gimp_item_linked_transform (GimpItem *item,
g_return_if_fail (gimp_item_is_attached (item));
g_return_if_fail (progress == NULL || GIMP_IS_PROGRESS (progress));
list = gimp_image_item_list_get_list (gimp_item_get_image (item), item,
GIMP_ITEM_TYPE_ALL,
GIMP_ITEM_SET_LINKED);
image = gimp_item_get_image (item);
list = gimp_image_item_list_filter (item, list);
items = gimp_image_item_list_get_list (image, NULL,
GIMP_ITEM_TYPE_ALL,
GIMP_ITEM_SET_LINKED);
gimp_image_item_list_transform (gimp_item_get_image (item), list, context,
items = gimp_image_item_list_filter (NULL, items);
gimp_image_item_list_transform (image, items, context,
matrix, direction,
interpolation_type,
clip_result, progress);
g_list_free (list);
g_list_free (items);
}

View File

@ -227,10 +227,6 @@ gimp_flip_tool_transform (GimpTransformTool *trans_tool,
break;
}
if (gimp_item_get_linked (active_item))
gimp_item_linked_flip (active_item, context, options->flip_type, axis,
FALSE);
if (orig_buffer)
{
/* this happens when transforming a selection cut out of a
@ -251,7 +247,16 @@ gimp_flip_tool_transform (GimpTransformTool *trans_tool,
{
/* this happens for entire drawables, paths and layer groups */
gimp_item_flip (active_item, context, options->flip_type, axis, FALSE);
if (gimp_item_get_linked (active_item))
{
gimp_item_linked_flip (active_item, context,
options->flip_type, axis, FALSE);
}
else
{
gimp_item_flip (active_item, context,
options->flip_type, axis, FALSE);
}
}
return ret;

View File

@ -1268,14 +1268,6 @@ gimp_transform_tool_real_transform (GimpTransformTool *tr_tool,
progress = gimp_progress_start (GIMP_PROGRESS (tool), FALSE,
"%s", tr_tool->progress_text);
if (gimp_item_get_linked (active_item))
gimp_item_linked_transform (active_item, context,
&tr_tool->transform,
options->direction,
options->interpolation,
clip,
progress);
if (orig_buffer)
{
/* this happens when transforming a selection cut out of a
@ -1306,17 +1298,29 @@ gimp_transform_tool_real_transform (GimpTransformTool *tr_tool,
{
/* this happens for entire drawables, paths and layer groups */
/* always clip layer masks so they keep their size
*/
if (GIMP_IS_CHANNEL (active_item))
clip = GIMP_TRANSFORM_RESIZE_CLIP;
if (gimp_item_get_linked (active_item))
{
gimp_item_linked_transform (active_item, context,
&tr_tool->transform,
options->direction,
options->interpolation,
clip,
progress);
}
else
{
/* always clip layer masks so they keep their size
*/
if (GIMP_IS_CHANNEL (active_item))
clip = GIMP_TRANSFORM_RESIZE_CLIP;
gimp_item_transform (active_item, context,
&tr_tool->transform,
options->direction,
options->interpolation,
clip,
progress);
gimp_item_transform (active_item, context,
&tr_tool->transform,
options->direction,
options->interpolation,
clip,
progress);
}
}
if (progress)

View File

@ -154,6 +154,7 @@ app/core/gimpimage-undo-push.c
app/core/gimpimagefile.c
app/core/gimpitem.c
app/core/gimpitem-exclusive.c
app/core/gimpitem-list.c
app/core/gimplayer-floating-sel.c
app/core/gimplayer.c
app/core/gimplayermask.c