[PATCH] d2d: Suppress last empty segment also for D2D1_FIGURE_END_OPEN

Stefan Brüns stefan.bruens at rwth-aachen.de
Mon Jan 3 10:59:19 CST 2022


On Montag, 3. Januar 2022 16:40:50 CET you wrote:
> On Mon, 3 Jan 2022 at 15:10, Stefan Brüns <stefan.bruens at rwth-aachen.de> 
wrote:
> > On Montag, 3. Januar 2022 12:58:50 CET you wrote:
> > > On Fri, 31 Dec 2021 at 08:23, Stefan Brüns
> > > <stefan.bruens at rwth-aachen.de>
> > 
> > wrote:
> > > > When the last vertex is coincident with the first vertex, the last
> > > > segment should be suppressed for both END_OPEN and END_CLOSED.
> > > > 
> > > > When the last, zero length segment is not omitted
> > > > d2d_geometry_intersect_self will add invalid segments.
> > > 
> > > Unfortunately, I don't think that's correct. For an END_OPEN figure,
> > > the first and last vertex coinciding doesn't imply that the last
> > > segment is a zero-length segment.
> > 
> > Please supply an example where coinciding does not mean zero length.
> > 
> > Last vertex refers to the second vertex of the last segment, not its start
> > vertex.
> 
> Consider for example a triangle like this:
> 
>      p0, p3
>        /\
>       /  \
>      /____\
>    p1      p2
> 
> and the corresponding Direct2D calls:
> 
>     BeginFigure(p0, ...);
>     AddLine(p1);
>     AddLine(p2);
>     AddLine(p3);
>     EndFigure(END_OPEN/END_CLOSED);
> 
> In the END_CLOSED case, we'd first create three segments:
> 
>     p0->p1
>     p1->p2
>     p2->p3
> 
> and then we'd have a fourth implicit zero-length segment p3->p0. By
> removing the p3 vertex, we replace the p2->p3 and p3->p0 segments with
> an implicit p2->p0 segment.
> 
> In the END_OPEN case however, we just have the three explicit segments
> above, without the implicit p3->p0 segment. In that case, removing the
> p3 vertex simply removes the p2->p3 segment, and we'd be left with the
> following figure:

Seems my explanation was somewhat unclear ...

I do not want to remove the last vertex (p3), but the last segment. In the 
current code, vertex_type[3] (using your example) for p3->p0 is always marked 
as TYPE_LINE (see EndFigure code). In case of p0 == p3, this causes troubles 
in the intersection code. In case p0 != p3, the p3->p0 segment must be a line 
(for intersection tests and filling), regardless if END_OPEN or END_CLOSED. 
The only difference between OPEN or CLOSED is the stroking of the p3->p0 
segment.

What seems to work quite fine is setting the TYPE for the last vertex 
(vertex_type[3]) to either TYPE_LINE for non-coincident p3/p0, or TYPE_END 
(newly added type) otherwise. (TYPE_NONE is already overloaded and can't be 
used.)

For my current approach, see
https://build.opensuse.org/package/view_file/
home:StefanBruens:branches:Emulators/wine/0003-d2d1-Skip-last-empty-segment-
in-intersection-tests.patch?expand=1&rev=19

Regards, Stefan


-- 
Stefan Brüns  /  Bergstraße 21  /  52062 Aachen
home: +49 241 53809034     mobile: +49 151 50412019
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 195 bytes
Desc: This is a digitally signed message part.
URL: <http://www.winehq.org/pipermail/wine-devel/attachments/20220103/22efcec7/attachment.sig>


More information about the wine-devel mailing list