IMPROVEMENTS:
- PNG export now supports alpha surfaces, which are just exported to greyscale. #60
This release introduces large changes to the layout of the library to better define the lines between managed and unmanaged architecture, similar to Zig's memory-centric use of the terms.
UNMANAGED API
All individual components of z2d now operate under an unmanaged model. This
especially goes for Surface
and Path
, which used to hold allocators in the
past, but no longer do. Both Surface
and Path
now offer static buffer
capabilities as well, allowing one to deal with allocation through other means
if one desires. Static buffer methods are almost entirely infallible (save some
checking that needs to be done for current points in Path
).
StaticPath
has also been introduced as a shorthand to working with a static
buffer Path
. This wraps a buffer of a particular length so that you don't
have to declare one separately. Additionally, all methods in StaticPath
are
100% infallible, with ones that would normally return non-memory errors causing
safety-checked undefined behavior in the event these errors would be returned.
The new unmanaged API also introduces the new painter
package, allowing you
to do fill or stroke operations without needing to use a Context
.
THE NEW MANAGED CONTEXT
Context
has now been completely overhauled to take the role as the sole
managed component in z2d. It holds a Path
of its own along with the Surface
and Pattern
that it did before 0.4.0, and more directly synchronizes settings
that are common to both path-level operations and fill/stroke, such as
transformation matrices and tolerance. Getters and setters exist for every
operation and it is now considered incorrect behavior to have to manipulate
context fields directly.
Most folks should be good using Context
for day-to-day operations, but if you
require more control (or wish to use the static buffer API), it exists as a
reference example of how you can use the unmanaged API yourself.
EXPLICIT ERROR SETS
All API calls now have explicit error sets defined. The error sets have been
defined with a granularity suiting the nature of the package. Most of the time,
memory errors are not a member of our library-level sets and are merged at the
site of the signature - this is for both readability and usability (e.g.,
Path.Error
can be returned on memory-infallible methods).
As part of this work, the global errors
package has been removed and errors
are now located within their respective structs or packages.
BUG FIXES:
- internal: removed the configurable edge FBA in the painter, in favor of a
small static FBA in a
StaticFallbackAllocator
. #53
TRANSFORMATION SUPPORT
0.3.0 adds support for transformations, both for Path
and Context
.
Transformations are represented by the traditional affine transformation matrix:
[ ax by tx ]
[ cx dy ty ]
[ 0 0 1 ]
Where the ax
, by
, cx
, and dy
values represent rotate, scale, and skew,
and tx
and ty
represent translation.
We currently offer operations for rotate
, scale
, and translate
via
methods on the transformation, other operations need to be composed on the
existing transformation via the mul
and inverse
methods. Additional methods
exist for converting co-ordinates from provided, un-transformed units (hereby
referred to as being in user space) into transformed ones (hereby referred to
as being in device space).
Transformations affect drawing in different ways depending on where they are applied:
- When set in a
Path
, transformations affect co-ordinates being plotted. Co-ordinates passed in tomoveTo
,lineTo
, etc., are expected to be passed in as user space and are transformed and recorded in device space. The transformation can be changed in the middle of setting points; this changes the device space for recorded points going forward, not the ones already recorded. This is ultimately how you will draw ellipses with thearc
command, and an abridged example now exists for drawing an ellipse by saving the current transformation matrix (CTM) for a path, addingtranslate
andscale
, executingarc
, and restoring the saved CTM. - When set in a
Context
, transformations mainly affect scaling and warping of strokes according to the setline_width
(which needs to be scaled withdeviceToUserDistance
prior to stroking in order to get the expected line width). This will be mostly obvious when working with a warping scale where the major axis will look thicker. Transformations currently do not affect filling. - Currently, synchronization of a
Context
andPath
transformation is an exercise left to the consumer.
Eventually, transformations will be extended to patterns when we implement more
than the simple single-pixel pattern, likely being simple raster
transformations on the source w/appropriate filtering/interpolation.
Additionally, it's expected that a transformation set in the Context
will
also affect line dashing when it is implemented, through transformation of the
dash pattern, and also affecting the capping as per normal stroking.
IMPROVEMENTS:
- internal: memory optimizations for the painter (mostly AA).
- #50
- Depending on the pixel source being used, this PR results in between 11%-55% less RAM used by AA rasterization based on the lack of extra allocations. Note that this is a theoretical estimate. YMMV, see the PR for more details and benchmarks.
BUG FIXES:
- internal: fix offset calculations for AA composition #46
- internal: ignore degenerate line_to when filling/stroking #47
FEATURES:
- New relative path
Path
helpers have been added:relMoveTo
,relLineTo
, andrelCurveTo
. #35 - Support for drawing arcs has been added to
Path
. Note that this only draws circles at the moment, ellipses will follow after transformation support has been added. #36 - Support for zero-length strokes. Only round cap behavior has been is available at the moment, square cap behavior will be added with dashed strokes. 0a040b0
BUG FIXES:
- internal: ensure incomplete polygons are not returned for filling #31
- Various stroke drawing fixes. (5cf163c, #38, #39, 155619d, 77b1d51, 68fd801)
Initial release.