Commit graph

5595 commits

Author SHA1 Message Date
Ell
3f43c2ea12 Issue #1554 - Select by Color tool does not select pixel(s) or area(s) of pixel(s)
In gimp_pickable_contiguous_region_by_color(), add a small epsilon
to the threshold value, to allow for small errors due to the input
color and pickable pixel-colors being converted to the common
format through different paths.

While we *could* special-case threshold == 0 when the input color
comes from the same pickable, as is the case for the select-by-
color tool, and perform an exact comparison in the original format,
in the more general case the input color can come from an arbitrary
source, such as a plug-in.

(cherry picked from commit a6c79770c3)
2019-02-28 09:27:48 -05:00
Ell
5d37a244dd app: merge layers in chunks, and show progress
In gimp_image_merge_layers() -- the internal function used by the
various layer-merging/flattenning functions -- process the merged-
layer graph in chunks, using gimp_gegl_apply_operation(), instead
of in one go, using gegl_node_blit_buffer().  Processing in chunks
better utilizes the cache, since it reduces the size of
intermediate buffers, reducing the chances of hitting the swap when
merging large images (see, for example, issue #3012.)

Additionally, this allows us to show progress indication.  Have the
relevant gimpimage-merge functions take a GimpProgress, and pass it
down to gimp_image_merge_layers().  Adapt all callers.

(cherry picked from commit e83d8ac4f2)
2019-02-25 05:10:59 -05:00
Ell
25ed35af62 app: accept a const GimpTempBuf in more temp-buf functions
In gimp_temp_buf_{ref,unref}(), and
gimp_temp_buf_create_{buffer,pixmap}(), accept a const GimpTempBuf
argument.

(cherry picked from commit 0a1e62768a)
2019-02-24 13:22:28 -05:00
Michael Natterer
db675d84e3 app: implement saving of GimpBrushPipes in the core
Just the GimpData::save() and ::copy() part that is needed to
duplicate and rename them, the image-to-pipe logic from the export
plug-in remains to be ported.

(cherry picked from commit aee097fa97)
2019-02-23 19:44:23 +01:00
Ell
a5130c7f66 app: add temp-buf-total varaible to the dashboard
Add a temp-buf-total variable to the dashboard's misc group,
showing the total size of all GimpTempBuf objects.

(cherry picked from commit bb645bae17)
2019-02-22 08:47:13 -05:00
Michael Natterer
45d3a054a4 app: some changes to GimpBrushPipe in preparation for .git image loading
- don't clear the names of the individual brushes, we need them for
  a load -> save roundtrip
- for the same reason, and for convenience, store the parameter string
  in the object
- clean up gimp_brush_pipe_finalize()

(cherry picked from commit 4b456e6079)
2019-02-19 23:48:09 +01:00
Ell
d424a418cb app: in GimpDrawableFilter, don't mask-out alpha comonent for alpha-less drawables
In gimp_drawable_filter_sync_affect(), don't mask-out the filter's
alpha component when the drawable doesn't have an alpha channel,
since this is no longer necessary -- we now explicitly convert the
output to the drawable format as part of the graph -- and it
prevents the gimp:mask-components node from becoming a NOP.

(cherry picked from commit af2c7d1b33)
2019-02-16 13:10:12 -05:00
Ell
353951a44f app: set/clear component-mask alpha-bit of alpha-less drawables, to make mask uniform
In gimp_drawable_get_active_mask(), when the drawable doesn't have
an alpha channel, set or clear the mask's alpha bit, according to
the state of the other bits, so that it never gets in the way of a
fully set/clear mask.  The value of the alpha bit doesn't matter
when there's no alpha channel, however, having a uniform mask
allows us to skip component masking altogether.

Additionally, provide a default implementation for
GimpDrawable::get_active_mask() which returns a full mask, and
remove the equivalent implementation for GimpChannel.

(cherry picked from commit 1b900bfa16)
2019-02-16 13:10:11 -05:00
Ell
116e8a6d4b app: remove gimp_drawable_replace_buffer()
Remove gimp_drawable_replace_buffer(), which is no longer used
anywhere since commits ddb69b77a7 and
3451ffb62c.  This eliminates
redundancy, since all compositing is now done through the layer-
mode code.

Furthermore, gimp_drawable_replace_buffer() used the drawable's
active-component array, whose layout depends on the image mode, as
an argument to gimp_gegl_replace(), which always expects an RGBA
component array, resulting in broken component masking in non-RGB
images.

(cherry picked from commit 2074accb60)
2019-02-14 11:05:19 -05:00
Jehan
0fef0a55f8 app: gimp_edgel_region_area() may return < 0 for non-closed zones.
The algorithm to compute a zone area by following its border only works
well for fully closed zones. It may return negative values otherwise.
Let's just assume the created zone is big in this case (which may or may
not be the case, but this is the safe case as it does not prevent
closure creation).

(cherry picked from commit 0636c302a3)
2019-02-14 13:54:24 +01:00
Jehan
b2fa4c6299 app: clarify function to validate line art closure.
Add some comments and string docs as it is not that obvious to
understand the whole logics, invert the return value (returning TRUE
when the closure line is accepted, instead of the opposite) and rename
it to more appropriate gimp_line_art_allow_closure().

(cherry picked from commit c4beca8c90)
2019-02-13 16:13:01 +01:00
Jehan
b2181d0fb2 app: proper signedness for return value of gimp_edgel_region_area().
It is just weird to return a negative area and multiply it by -1.
Just apply the proper signs from the start.

(cherry picked from commit 14e7424403)
2019-02-13 16:12:54 +01:00
Michael Natterer
376b053129 app: don't unref a NULL GimpTempBuf in gimp_pattern_copy()
(cherry picked from commit a95c169091)
2019-02-12 21:17:04 +01:00
Michael Natterer
cf76b7f73c app: implement brush saving in the core
and enable duplicating the clipboard brush, like for patterns.

(cherry picked from commit 1e6b26e83a)
2019-02-12 18:54:16 +01:00
Michael Natterer
3dc01393eb app: remove useless includes from gimppattern-save.c
(cherry picked from commit 831d04ec7e)
2019-02-12 18:47:06 +01:00
Michael Natterer
5dc78980f4 app: implement pattern saving in the core
Add GimpData::save() implementation to GimpPattern, and change some
glue code to make patterns editable.

Also implement GimpData::duplicate() in GimpPatternClipboard, which
makes it possible to simply copy an area and duplicate the clipboard
pattern to create a new persistent pattern.

(cherry picked from commit e93fd73fac)
2019-02-11 21:02:36 +01:00
Michael Natterer
616f5aac11 app, plug-ins: start consolidating brush and pattern loading/saving code
We currently have brush and pattern I/O code in both the core and
plug-ins. This commit starts removing plug-in code in favor of having
one copy of the code in the core, much like XCF loading and saving is
implemented.

Add app/file-data/ module with file procedure registering code, for
now just with an implementation of file-gbr-load.

Remove the file-gbr-load code from the file-gbr plug-in.

(cherry picked from commit a4e77e57f6)
2019-02-11 12:56:56 +01:00
Michael Natterer
270bd71658 app: add all missing festures from file-gbr-load to the core brush loader
gimp_brush_load_brush(): support legacy gpb brushes, and port a check
for gsize overflow what was added to the plug-in.

(cherry picked from commit 619f999280)
2019-02-11 12:36:02 +01:00
Jehan
5796cc46e4 app: improve line art bucket fill by filling unsignificant areas.
The line art imaginary segments/splines are not added when they create
too small zones, unless when these are just too small ("unsignificant").
Why the original algorithm keeps such micro-zones is because there may
be such zones created when several splines or segments are leaving from
a same key point (and we don't necessarily won't to forbid this). Also
we had cases when using very spiky brushes (for the line art) would
create many zones, and such micro-zones would appear just too often
(whereas with very smooth lines, they are much rarer, if not totally
absent most of the time).
Also it is to be noted that the original paper would call these
"unsignificant" indeed, but these are definitely significant for the
artists. Therefore having to "fix" the filling afterwards (with a brush
for instance) kind of defeat the whole purpose of this tool.

I already had code which would special-case (fill) 1-pixel zones in the
end, but bigger micro zones could appear (up to 4 pixels in the current
code, but this could change). Also I don't want to use the "Remove
Holes" (gimp:flood) operation as I want to make sure I remove only
micro-holes created by the line art closure code (not micro-holes from
original line arts in particular).

This code takes care of this issue by filling the micro-holes with
imaginary line art pixels, which may later be potentially bucket filled
when water-filling the line art.

(cherry picked from commit 72092fbdbc)
2019-02-07 18:42:46 +01:00
Ell
a335eb0e6e app: avoid unnecessary calls to gimp_temp_buf_data_clear()
Avoid unnecessary calls to gimp_temp_buf_data_clear() in various
places, where either the entire buffer is being written to, or most
of it is, only requiring clearing the edges.

(cherry picked from commit 9d19e804ed)
2019-02-06 16:51:07 -05:00
Ell
d39634a914 Issue #2372 - Reduced quality of the Parametric brush in 2.10
Promote the precision of generated brushes to 32-bit float, and
modify brush preview generation, and gimpbrushcore-loops, to handle
float brushes.  This avoids posterization in large brushes.

Note that non-generated brushes are still uint8.

(cherry picked from commit 8ef1113dee)
2019-02-06 14:30:56 -05:00
Ell
8f31f8fa3c app: add gimp_temp_buf_{lock,unlock}()
In GimpTempBuf, add gimp_temp_buf_lock() and gimp_temp_buf_unlock()
functions, which lock/unlock the buffer for data access.  Unlike
gimp_temp_buf_get_data(), which returns a direct pointer to the
buffer's data, the new functions take a format parameter and may
return a temporary buffer, allowing the buffer to be accessed using
an arbitrary format.

(cherry picked from commit 12dde445c4)
2019-02-06 14:30:55 -05:00
Ell
d6bb1efd77 app: in gimp_transform_matrix_generic(), apply matrix even if invalid
In gimp_transform_matrix_generic(), apply the resulting matrix even
if the transformation is invalid, since GimpGenericTransformTool
relies on the matrix to properly update the transform-grid widget.

(cherry picked from commit 59ef222c7f)
2019-02-04 16:48:54 -05:00
Ell
bcc44a08b1 app: fix indentation in gimpmaskundo.h
(cherry picked from commit 4db566f0e1)
2019-01-20 10:33:56 -05:00
Ell
8324aeba82 app: align mask-undo buffer to tile grid
In GimpMaskUndo, align the copied region to the source buffer's
tile grid, so that all copied tiles are COWed.

(cherry picked from commit 7cd768f3d8)
2019-01-20 10:07:33 -05:00
Ell
4c22313ce6 app: improve gimp_channel_clear()
When clearing a channel, do nothing if the channel is already
empty; otherwise, align the cleared rectangle to the channel
buffer's tile grid, so that all affected tiles are dropped, rather
than zeroed.  Furthermore, only update the affected region of the
channel.

(cherry picked from commit ac5e4f4c33)
2019-01-17 15:15:59 -05:00
Ell
858dbf6e18 app: update drawable filter upon alpha-lock change
In GimpDrawableFilter, when operating on a layer, update the filter
when the layer's lock-alpha flag changes.

(cherry picked from commit de4e7b4770)
2019-01-17 14:21:03 -05:00
Jehan
7700cb3d81 app: improved fix to commit 036ccc70cf.
After discussion with Sébastien Fourey and David Tschumperlé, it was
decided that a better fix for the edge case raised in #2785 was to add a
keypoint anyway, even if the point and none of its neigbours have a
positive smoothed curvature, yet they have a positive raw curvature. In
such case, we use the local maximum raw curvature instead of the local
maximum smoothed curvature.

(cherry picked from commit aa04258620)
2019-01-17 15:37:24 +01:00
Jehan
b35941ec4c Issue #2785: Fill by line art detection produces Segmentation fault...
... with some images.

(cherry picked from commit 036ccc70cf)
2019-01-17 15:37:24 +01:00
Ell
61a6b15a66 app: parallelize gimp_pickable_contiguous_region_by_color()
... by distributing the processed area over multiple threads.

(cherry picked from commit 8571d7812f)
2019-01-17 09:30:51 -05:00
Ell
cfd1d0463f app: convert gimppickable-contiguous-region to C++
(cherry picked from commit 9719dff9c5)
2019-01-17 09:30:50 -05:00
Jehan
32fdd69324 app: add the concept of line art source to Bucket Fill tool.
Additionally to sample merge and active layer, now we can only use the
layer above or below the active layer as line art source.

The line art fill is meant to work on drawing lines. Though sample merge
still is ok in many cases, the more you fill with colors, the more the
line art computation becomes unecessarily complex. Also when you use a
lot of layers with some of them already filled with colors, it makes it
impossible to colorize some line art zones with the tool. Moreover you
just don't want to have to hide every layers out there to colorize one
layer (especially background layers and such as you may want to see the
result with your background).
Thus we want to be able to set the source as a unique layer, while it
not being necessarily the active one (because you want lines and colors
on different layers). In this case, I am assuming that the color and the
line layers are next to each other (most common organization).

(cherry picked from commit c71b4916af)
2019-01-15 17:39:17 +01:00
Ell
fe5ee0f7b8 app: clear priority rect when finishing projection rendering
In gimp_projection_finish_draw(), clear the chunk iterator's
priority rect before finishing rendering, since it's not needed at
this point, and this is slightly more efficient.

(cherry picked from commit 9833da3431)
2019-01-13 08:23:05 -05:00
Jehan
4fd8e4841f app: add link to Smart Colorization scientific paper.
This is sometimes asked, and myself also need to find it from time to
time. I may as well put the link inside the code comments, where it is
just easy to find!

(cherry picked from commit 005bc1406b)
2019-01-12 18:03:24 +01:00
Ell
dfc038e650 app: in gimp_projection_chunk_render_start(), properly invalidate preview
In gimp_projection_chunk_render_start(), when the current
projection rendering is complete, but not finalized yet, and no new
rendering is started (since the current update region is empty),
make sure to invalidate the projectable's preview, since it
normally happens when rendering is finalized, which doesn't happen
in this case.

(cherry picked from commit 42845c9462)
2019-01-12 08:33:24 -05:00
Ell
f21eec319f app: in gimp_projection_chunk_render_start(), don't leak empty region
In gimp_projection_chunk_render_start(), don't leak the current
update region when it's empty, but not NULL, and properly shut down
the idle source.

(cherry picked from commit 0e5de95760)
2019-01-12 08:20:16 -05:00
Ell
4cbec7608f app: fix gimp_chunk_iterator_set_priority_rect()
(cherry picked from commit 942e1aa939)
2019-01-12 07:32:08 -05:00
Ell
5e00c26295 app: in gimpchunkiterator.c, #include <stdlib.h>
... for qsort().

(cherry picked from commit a61f29e30a)
2019-01-12 06:16:50 -05:00
Ell
b62e3fd3b8 app: use GimpChunkIterator in GimpProjection
Replace the custom chunking logic of GimpProjection with
GimpChunkIterator, added in the previous commit.

(cherry picked from commit 246e782858)
2019-01-12 04:53:11 -05:00
Ell
8c31ed6f02 app: add GimpChunkIterator
Factor out the region-chunking logic of GimpProjection into a new
GimpChunkIterator type, providing a generic mechanism for iterating
over a cairo region in discrete chunks.  The iterator doesn't
perform any processing itself, but rather dispenses rectangular
chunks, which the user then processes.

Iteration is broken into intervals, the duration of which is
configurable.  Each iteration begins with a call to
gimp_chunk_iterator_next(), after which
gimp_chunk_iterator_get_rect() should be called in succession to
fetch a rectangle to process, until it returns FALSE, which marks
the end of the iteration.  Updates to the UI should take place in
the interval between iterations, but not during an iteration.  The
iterator dynamically adjusts the chunk size according to processing
speed, in order to match the target iteration interval.

The iterator can be given a priority rectangle, which is processed
before the rest of the region.  It can also be given a
representative tile rectangle, defining a regular tile grid;
dispensed chunks are aligned to the tile grid as much as possible.

(cherry picked from commit ba9ce34e10)
2019-01-12 04:53:10 -05:00
Jehan
e0be9bdef2 app: alt-click to pick a layer will loop through candidate layers.
If you click on a zone filled in several visible layers, you don't
necessarily want the top layer. You may want one below. With this
change, as long as you hold alt, you will loop through all candidate
layers from top to bottom (then looping back top when reaching the
bottom).
In a first alt-click, you will always end up to the top candidate.

(cherry picked from commit 90e9eb3fca)
2019-01-08 13:41:06 +01:00
Ell
0f2f95d97b app: in bucket-fill tool, avoid calculating line art when not in line-art mode
In the bucket-fill tool, don't pre-calculate the line art when not
using a line-art fill area.  Also, misc. cleanup.

(cherry picked from commit 823d4a0d24)
2019-01-06 16:31:11 -05:00
Ell
fbf73bee70 app: remove gimp-scratch; replace with gegl-scratch
The scratch allocator has been moved to GEGL (commit
gegl@b99032d799dda3436ffa8c1cc28f8b0d34fb965d).  Remove gimp-
scratch, and replace all its uses with gegl-scratch.

(cherry picked from commit 889e2e26ee)
2019-01-06 07:39:52 -05:00
Ell
8142fe4d1c app: In GimpHistogram, align copied buffer region to tile rect
In gimp_histogram_calculate_async(), align the copied region of the
drawable and mask buffers to the tile grid, so that all copied
tiles are COWed.

(cherry picked from commit d56d663eaa)
2019-01-04 08:17:42 -05:00
Michael Natterer
a27f7c7724 Issue #1788 - Inconsistency between FG color and selected color in...
...palette views despite selected color being in the currently
selected pallette

As suggested by Massimo, changing the color comparison EPSILON in
gimppalette.c from 1e-10 to 1e-6 fixes this, and is really small
enough.

Also, generally clean up color comparison epsilons:

- use a #define, not hardcoded values for all uses of
  gimp_rgb[a]_distance()
- call the #defines RGB_EPSILON and RGBA_EPSILON
- make them all 1e-6 or larger

(cherry picked from commit abd7cbfc8d)
2019-01-02 01:53:02 +01:00
Michael Natterer
d6ca6d510e Issue #2667 - When copying a text layer, paste should create a new...
...text layer, not an image of the text

In gimp_edit_paste_get_layer(), when pasting as floating selection,
collapse the pasted layer into an ordinary layer only if it's a group
layer. There is nothing that speaks against having a floating text
layer, it works just fine.

(cherry picked from commit 8a4aacb52f)
2019-01-02 00:17:45 +01:00
Ell
e61188e666 app: small fix to gimp_drawable_edit_fill()
(cherry picked from commit 3738ff3ffd)
2018-12-31 05:33:45 -05:00
Ell
5d905d1d65 app: in gimp_drawable_edit_fill(), make trivial alpha-only fill a NOP
In gimp_drawable_edit_fill(), if the fill only affects the alpha
channel, and if the drawable has no alpha channel, or the alpha
channel is masked out, do nothing, instead of unnecessarily
performing the fill, which has no effect.

(cherry picked from commit 6384ff01b6)
2018-12-31 04:40:18 -05:00
Ell
a330a94b94 app: in GimpDrawableFilter, only update crop/preview area when updating whole drawable
In GimpDrawableFilter, when updating the entire filter area, only
update the crop/preview area (as set by
gimp_drawable_filter_set_{crop,preview}()), instead of the entire
drawable.

(cherry picked from commit b846ffed19)
2018-12-30 05:13:30 -05:00
Ell
05f74b6f40 app: add gimp_drawable_filter_set_crop()
Add gimp_drawable_filter_set_crop(), which allows setting an output
crop rectangle for the filter; anything outside the rectangle
doesn't get filtered.  The crop area is combined with the preview
area to determine the filtered area during preview, however, unlike
the preview area, the crop area remains in effect while committing
the filter.

Consequently, when merging a drawable filter, if the filter has a
crop, only process the cropped area.

(cherry picked from commit 5c27d14fdf)
2018-12-30 05:13:29 -05:00