Footprint algorithms: in the stamp, or in the paintop?

Boudewijn Rempt boud at valdyas.org
Thu Mar 27 19:58:57 CET 2008


On Wednesday 26 March 2008, emanuele at valinor.it wrote:

> Again, I tried to keep ideas compatible with boud work... And they are,
> right?

I'm not sure... I had to drop out of the discussion yesterday because I had a 
busy day at work and during the evening got distracted by something else, but 
I had started a design document describing what I am working on, which I 
reproduce herewith:

-------------

All I wanted to do initially was to refactor our current code to make
more sense, fix a number of problems and share configuration settings
and widgets among similar paintops (i.e. like the pressure curve-based
settings used in brushop and smudgeop that would also be useful for the
other KisBrush-using paintops.) 

I really don't want to refactor more than absolutely necessary, so I'm not 
going to do any renaming for now -- I don't think we can get consensus on 
that.

Also, I don't see any useful benefit of creating classes that apply a 
collection of presets and use those from the paintops, because that is 
exactly what a paintop is, basically. However, it's not unlikely that
we can coalesce most of the KisBrush-based paintops into one paintop with a 
good collection of presets.

KoResource

    KisBrush                interface for "tip"-like resources. A KisBrush
                            or descendant provides a KisPaintDevice
                            that represents either a mask (grayscale)
                            or a colored image, depending on the subtype
                            of the KisBrush. This mask represents a
                            single footprint (following the Shoup
                            model[1]). KisBrush and descendants can
                            select different, possibly pregenerated,
                            footprints based on parameters given in
                            KisPaintInformation, scaleX, scaleY, angle
                            and subpixel position. It is important that
                            this does not change since it is necessary
                            to pre-generate and cache footprints for
                            preformance reasons.

        KisGbrBrush         .gbr files (to be newly created)
        KisAutoBrush        rect or elliptical tips
        KisImagePipeBrush   .gih files (contain images or masks, maybe more 
                            than one print, that can be selected based on the 
                            contents of the "parasites".)
        KisTextBrush        painting with a chunk of text

    KisPaintOpPreset        a named resource that contains the settings of
                            a paintop, can show a demonstration stroke
                            and can be used by the KisPaintOpRegistry
                            to create a paintop instance.

KisPaintOpRegistry          loads all KisPaintOpPlugins. Given a 
                            KisPaintOpPreset, creates (or retrieves a cached) 
                            KisPaintOp instance using a KisPaintOpFactory. 

KisPaintInformation         state information that's kept from
                            stroke to stroke, like the vector,
                            pressure, rotation, tilt, rate etc.
    
KisPaintOpSettings          serializable settings for paintops,
                            like the pressure curve for darken etc.

KisPaintOpOption            an option page that can be shown in the
                            paintop preset widget, for instance, the 
                            darken option is a toggle and
                            has an option custom curve. Is possibly
                            associated with a KisPaintOpManipulator,
                            although some options will be, for performance
                            reasons, built-in in the base KisPaintOp
                            (like sizeForPressure, darkenForPressure,
                            opacityForPressure). KisBrush choice is another
                            KisPaintOpOption.

KisPaintOpManipulator       (to use Emanuele's name). A filter that takes as 
                            input KisPaintInformation, a KisPaintOpOption
                            and the dab and modifies that dab using the
                            input data. An example could be a rotate or
                            a jitter KisPaintOpManipulator. Not all paintops
                            need to use the manipulators and not all paintops
                            that do need to support all manipulators. Paintops
                            do the chaining of the manipulators, if they use
                            them. Manipulators only work for dab-based
                            paintops.

KisPaintOpBox               The gui class that presents the available paintops
                            and presets to the user. There will be a number of
                            presets shown in the toolbox, and a dropdown box 
                            to select more presets, edit the current preset
                            and add, remove, rename existing presets. The
                            KisPaintOpOptions are shown in the preset editor.

KisPaintOp                  A pluggable brush engine that renders a stroke 
                            from KisPaintInformation to
                            KisPaintInformation using the settings in
                            KisPaintOpSettings.  KisPaintOps can use other
                            KisPaintOps to pre-render a stroke. Selection
                            of another paintop is through a preset, so no
                            recursive configuration.  Has the following
                            subclasses (with the settings each subclass
                            supports; it may be advantageous to combine
                            some paintops in one paintop with presets
                            for the variations):

    KisAirbrushOp           KisBrush, subpixel, tangential pressure, tilt
    KisBrushOp              KisBrush, subpixel, pressure (opacity, darken,
                            size)
    KisConvolveOp           Not implemented
    KisCPaintOp             pressure(bristle positioning)
    KisDuplicateOp          KisBrush, subpixel, healing, offsetx, offsety, 
                            perspective correction
    KisDynamicOp            experimental, uses its own settings system
    KisEraseOp              KisBrush, subpixel, pressure (size)
    KisFilterOp             KisBrush
    KisPenOp                KisBrush, pressure(size)
    KisSmudgeOp             KisBrush pressure(rate, size, opacity)

KisToolPaint
    KisToolFreehand         base class for freehand tools. Can do fun stuff
                            like smoothing lines.
        KisToolBrush        to be merged with KisToolFreehand?
        KisToolSelectBrush  to be deleted; we're exposing the selection masks
                            ready for painting on
        KisToolSelectEraser ditto.


So -- the user selects a certain preset and a tool. The tool asks the
paintop registry for a fully configured paintop based on the active
preset. The tool creates a KisPainter on the current paint device (layer,
mask or selection) or a temporary paint device, and then determines
the begin and the end point of a paint action, then asks the painter to
either paint a line or a curve between those points. The painter then
asks the paintop to paint a stroke. The paintop is free to do whatever
it is programmed for:

If it's a KisBrush based paintop, determine the basic dab (KisBrush),
manipulate the dab until it has its final shapei (KisPaintOpManipulator),
then compose the dab with the paint device.

If it's a programmable paintop, it works through the various programs and
paints its stroke.

If it's a paintop that needs another paintop, it lets the other paintop
compute the stroke and then does its own thing with the result and the
paint device it is working on. (This may be useful for, for instance,
the filter paintop)

If it's a sumi-e paintop, it computes bristle positions and ink levels, 
determines the stroke and paints that.

If it's another paintop, it does something else again: paintops are free
to be implemented any way the author wants.


[1] Shoup model: http://www.rgshoup.com/prof/SuperPaint/.

-- 
Boudewijn Rempt 
http://www.valdyas.org/fading/index.cgi


More information about the kimageshop mailing list