<html><head></head><body><div class="ydp51abfe55yahoo-style-wrap" style="font-family:Helvetica Neue, Helvetica, Arial, sans-serif;font-size:16px;"><div></div>
        <div>I'd just like to raise two points: </div><div><br></div><div>- while the rendering system cannot be specified to cope with arbitrary amount or type of font brokenness, the problem with disallowing implied on-curve cubic points, or mandating that off-curve cubic points must be in pairs, is that off-curve points (and implied on-curve points) are very frequently used and beneficial in quadratics. You shouldn't take away capability that is not only allowed, but encouraged.</div><div><br></div><div>- suggestions about multiple passes - either as a QA process overall, or as part of the rendering process, sounds a lot like passing the bucket to me. For the former, it definitely sounds like 'let somebody else worry about it and / or fix the font for me' . As for the latter - I think it might be some significant resistance / re-engineering for some of the existing "production" rendering systems. Most of them are designed with doing things quickly, and in case of problems, try to do something not too crazy and move on. Doing multiple passes to figure out what's the font designers' actual intention isn't on the table.</div><div><br></div><div>Dropping all cubic bits in case of inconsistency is not a bad idea - for an entirely off-curve set of points, you get double the numbers of points and get probably a rendered contour close to each of those. (That's basically the current quadratics usage).</div><div><br></div><div><br></div>
        
        <div id="ydp51abfe55yahoo_quoted_7139437167" class="ydp51abfe55yahoo_quoted">
            <div style="font-family:'Helvetica Neue', Helvetica, Arial, sans-serif;font-size:13px;color:#26282a;">
                
                <div>
                    On Monday, 2 October 2023 at 21:28:13 BST, Behdad Esfahbod <behdad@behdad.org> wrote:
                </div>
                <div><br></div>
                <div><br></div>
                <div><div id="ydp51abfe55yiv8483794767"><div><div dir="ltr"><div dir="ltr">On Sat, Sep 23, 2023 at 2:01 PM Skef Iterum <<a shape="rect" href="mailto:skef@skef.org" rel="nofollow" target="_blank">skef@skef.org</a>> wrote:<br clear="none"></div><div class="ydp51abfe55yiv8483794767gmail_quote"><blockquote style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex;" class="ydp51abfe55yiv8483794767gmail_quote"><u></u>

  
    
  
  <div>
    <p>I would say this cross-context pattern for "undefined behavior"
      is reasonably common across distributed media systems:</p>
    <ol><li>End-stage processors are "forgiving" -- they try their best to
        do something that makes sense</li><li>Intermediate sanity-checkers and sanitizers are "unforgiving"
        -- they flag undefined behavior for rejection</li></ol>
    <p>Most font files go through some context where 2 can be enforced
      before they reach an end-user. OS vendors check the fonts they
      include. Adobe's font marketplace has checks. I believe Google
      checks the fonts that go up on its servers. (Browsers also check
      fonts before using them, but that may be too late for checking
      subtleties like what we're discussing.)<br clear="none">
    </p>
    <p>I would say this a good convention overall. Forcing all behavior
      to be defined can cut off options for defining that behavior in
      the context of future features.<br clear="none">
    </p>
    <p>The trickier question is what to do about changes in undefined
      behavior -- either making something undefined that wasn't before,
      or somehow changing the status of behavior that wasn't defined in
      the spec but that all implementers handled in a certain way. I
      doubt we're doing the former but we have to be careful about the
      latter because fonts that are already out there and working will
      start to break.</p>
    <p>I'll also note here that I argued in my initial response doc that
      there is less motivation for interpolated on-curve cubic points
      than there is for quadratics. I suspect you'll mainly see them in
      circles and other symmetric curves (like some "o"s and "O"s), and
      they will save space, but the arguments for them are much weaker
      than in the quadratic case. (I doubt you'll seem them creep up
      into the UI of design tools like you sometimes do for quadratic
      interpolated points (e.g. in FontForge).) So we should consider
      whether they're worth the confusion they will add. There are lots
      of features one <i>could</i> add that would save two bytes here
      and four bytes there, and it seems like this is being proposed
      mostly because of the precedent with quadratics. <br clear="none">
    </p>
    <p></p></div></blockquote><div><br clear="none"></div><div>Thanks Skef and others. But even if we fully disallow implied on-curves for cubics, we still have the same problem of defining what happens when we encounter such segments.</div><div><br clear="none"></div><div>As for the Jonathan's suggested in the other thread to either NOT render the misbehaving contour or fully describe how to render it, when designing the current model I had two goals in mind:</div><div><br clear="none"></div><div>  - We should be able to continue to process one point at a time (keeping a state of course) and calling moveto/lineto/curveto/qcurveto.</div><div><br clear="none"></div><div>  - Reversing the contour points and ends should produce the same shape with opposite winding direction.</div><div><br clear="none"></div><div>Both of these will be violated by the suggested models. If we can find a way to fully specify the system while retaining these two properties, that's my preference. Otherwise, it looks like NOT rendering the contour at all can be achieved by an extra pass on the points before doing any drawing for the contour.</div><div id="ydp51abfe55yiv8483794767yqtfd15765" class="ydp51abfe55yiv8483794767yqt6605459831"><div><br clear="none"></div><div>b</div><div> </div><blockquote style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex;" class="ydp51abfe55yiv8483794767gmail_quote"><div><p>Skef<br clear="none">
    </p>
    <div>On 9/23/23 12:02, Laurence Penney
      wrote:<br clear="none">
    </div>
    <blockquote type="cite">
      <pre>[Moving discussion to its own thread]

In the following document recently posted by Vlad:
<a shape="rect" href="https://github.com/harfbuzz/boring-expansion-spec/blob/main/iso_docs/WG03_otf-improvements.pdf" rel="nofollow" target="_blank">https://github.com/harfbuzz/boring-expansion-spec/blob/main/iso_docs/WG03_otf-improvements.pdf</a>

We have the following:

</pre>
      <blockquote type="cite">
        <pre>3.1. Specification Change
Add the following flag to the Simple Glyph Description section's Simple Glyph Flags:
Mask Name Description
0x80 CUBIC Bit 7: Off-curve point belongs to a cubic-Bezier segment
There are several restrictions on how the CUBIC flag can be used. If any of the
conditions below are not met, the behavior is undefined.
The number of consecutive cubic off-curve points within a contour (without wrap-
around) must be even.
All the off-curve points between two on-curve points (with wrap-around) must either
have the CUBIC flag clear, or have the CUBIC flag set.
The CUBIC flag must only be used on off-curve points. It is reserved and must be set
to zero for on-curve points.
</pre>
      </blockquote>
      <pre>Discussion in another thread between Hin-Tak Young, Jonathan Kew and Laurence Penney has raised issues about the wisdom of the phrase "the behavior is undefined", rather than specifying a behaviour when these bits are in an unsupported configuration.

Hin-Tak notes that if one influential implementation accepts such non-compliant fonts and renders the glyph in a particular way, then other implementations will be tempted to follow it.

Jonathan: "I think the spec should *either* state that if the glyph data violates these "must" requirements, nothing will be rendered for that glyph; *or else* it should clearly specify how "anomalous" cases -- such as the CUBIC flag being set on a single off-curve point -- are to be processed, so that implementations produce a consistent result. One possible way forward, for example, would be to specify that for any contour where the CUBIC flag is used in violation of the rules given, all CUBIC flags must be ignored and the contour processed entirely according to legacy TrueType quadratic behavior. Leaving it explicitly undefined pretty much guarantees that implementations will come up with incompatible results, and fonts will get created that (inadvertently) depend on one implementation's behavior."

I (Laurence) noted that that "undefined behaviour" already appears several times in the OFF spec, and in practice real-world font processor are quite forgiving. If "undefined behaviour" is not permitted here it should probably be reviewed in those other places. Jonathan’s proposal to ignore all cubic bits in any non-conforming contour sounds workable, even though such error-handling behaviour is rare in OFF.

- Laurence

_______________________________________________
mpeg-otspec mailing list
<a shape="rect" href="mailto:mpeg-otspec@lists.aau.at" rel="nofollow" target="_blank">mpeg-otspec@lists.aau.at</a>
<a shape="rect" href="https://lists.aau.at/mailman/listinfo/mpeg-otspec" rel="nofollow" target="_blank">https://lists.aau.at/mailman/listinfo/mpeg-otspec</a>
</pre>
    </blockquote>
  </div>

_______________________________________________<br clear="none">
mpeg-otspec mailing list<br clear="none">
<a shape="rect" href="mailto:mpeg-otspec@lists.aau.at" rel="nofollow" target="_blank">mpeg-otspec@lists.aau.at</a><br clear="none">
<a shape="rect" href="https://lists.aau.at/mailman/listinfo/mpeg-otspec" rel="nofollow" target="_blank">https://lists.aau.at/mailman/listinfo/mpeg-otspec</a><br clear="none">
</blockquote></div></div></div><div id="ydp51abfe55yiv8483794767yqtfd24127" class="ydp51abfe55yiv8483794767yqt6605459831">
</div></div></div><div class="ydp51abfe55yqt6605459831" id="ydp51abfe55yqtfd89355">_______________________________________________<br clear="none">mpeg-otspec mailing list<br clear="none"><a shape="rect" href="mailto:mpeg-otspec@lists.aau.at" rel="nofollow" target="_blank">mpeg-otspec@lists.aau.at</a><br clear="none"><a shape="rect" href="https://lists.aau.at/mailman/listinfo/mpeg-otspec" rel="nofollow" target="_blank">https://lists.aau.at/mailman/listinfo/mpeg-otspec</a><br clear="none"></div></div>
            </div>
        </div></div></body></html>