SourceForge.net Logo Home Page Project Page Download CVS repository
<set-vectors> <with-vectors> <set-projection-vector> <with-projection-vector> <set-freedom-vector> <with-freedom-vector> <set-dual-projection-vector> <store-projection-vector> <store-freedom-vector>

Vectors

A vector is a direction represented by a line. The TrueType engine stores a vector as an x,y coordinate pair--that is, as one end-point of a line. The other end-point of the line that defines a vector is always at coordinate 0,0. The actual location of the line is not so important, however, as the direction the line defines. Vectors stored by the TrueType engine determine how measurements are made and how points are moved.

The TrueType engine maintains three vectors:

Most of the time the three vectors all point in the same direction, with the result that it is easy to visualize how instructions that move points work. For example, this code

<with-vectors axis="x">
  <move distance="left-sidebearing">
    <reference>
      <point num="a"/>
    </reference>
    <point num="b"/>
  </move>
</with-vectors>

moves point b along the horizontal freedom vector until it is positioned the rounded distance "left-sidebearing" from point a (the character origin at 0,0), as measured along the horizontal projection vector. When measuring the distance and moving the point, the TrueType engine treats both a and b as if they were arrayed in a single dimension, and the y axis did not exist. These images illustrate the effect of the move:

before move of point b after move of point b

The freedom and projection vectors need not match. In the leftmost image below, the glyph program has moved point a, which defines the top of a serif, up to the nearest gridline. As a result point b is too close to a and ought to be moved up by the same amount. But moving it straight up would alter the slope of the diagonal line whose bottom point it defines. The solution is to set the freedom vector to be parallel to the diagonal so that point b moves along that line without distorting it. This code will do it:

<with-projection-vector axis="y">
  <with-freedom-vector to-line="parallel">
    <line>
      <point num="b"/>
      <point num="c"/>
    </line>
    <shift>
      <reference>
        <point num="a"/>
      </reference>
      <point num="b"/>
    </shift>
  </with-freedom-vector>
</with-projection-vector>

The middle image shows the result of the move, and the last image shows the same area of the glyph after execution of <interpolate-untouched-points>.

before move of point b after move of point b after move of point b

Notice how the curve that joins the diagonal to the serif is preserved even at 16 pixels-per-em. An anti-aliasing program can give an impression of this curve, as in the image below, which is enlarged 8x.

before move of point b

A vector has a direction, though this is rarely significant. When the vector is set to the y axis, it points up; when set to the x axis, it points right. When set to a line, it points from the second point in the <line> element to the first: imagine an arrow on the first point.

Instructions that set vectors

Instructions that begin with set set one or two vectors, and these remain as set until another vector-setting instruction is encountered. Instructions that begin with with set vectors that apply only to the instructions contained within the with element.

Instructions that set the projection vector, freedom vector, or both may do so in any of four ways:

<set-vectors>
<with-vectors>

Sets both the projection vector and the freedom vector to the same value. They can be set to "x" or "y" via the axis attribute; to a line by including a line element as the content of the <set-vectors> element or the first child of the <with-vectors> element; or by passing "raw" values via the x-component and y-component attributes.

Xgridfit looks first for an axis attribute, next for a <line>, and finally for x-component and y-component attributes (neither is used unless both are present). If it finds none of these, Xgridfit prints a warning and attempts to find the values it needs on the stack.

The "raw" values passed in via x-component and y-component are constrained in ways that make them difficult to calculate, at least in a TrueType program, but the x-component/y-component method is useful to restore values that have been saved via <store-projection-vector> or <store-freedom-vector>. For example, to copy one vector to another, you can do this:

<variable name="x-comp"/>
<variable name="y-comp"/>
<store-freedom-vector x-component="x-comp" y-component="y-comp"/>
<set-projection-vector x-component="x-comp" y-component="y-comp"/>

But because of the way these instructions can leave values on the stack and take them from the stack again, this is easier and more efficient:

<store-freedom-vector/>
<set-projection-vector/>

When setting vectors to a line, one or both points in the line can be in the twilight zone. You can include a zone attribute in the <line> element or one in either or both <point> elements. Include a zone attribute in the <line> element if both points are in the twilight zone. This is the same as including an attribute zone="twilight" in both points. If only one point is in the twilight zone, include the zone attribute for that point.

Attributes

axis
The axis to which the vectors should be set. Permitted values are x and y.
to-line
Whether the vectors should be parallel or orthogonal (perpendicular) to the line being used to set the vector. The default value is parallel.
x-component
The x component of the vector to set. This has no effect unless the y-component attribute is included as well.
y-component
The y component of the vector to set. This has no effect unless the x-component attribute is included as well.

<set-projection-vector>
<with-projection-vector>

Just like <set-vectors>, but sets only the projection vector.

<set-freedom-vector>
<with-freedom-vector>

Just like <set-vectors>, but sets only the freedom vector.

<set-dual-projection-vector>

Like <set-projection-vector>, but the dual projection vector can be set only from a line, and it uses the original positions in the outline of the points that constitute the line rather than their current positions (assuming they have moved).

The dual projection vector is not used by every instruction: just by <interpolate>, <get-coordinate>, <measure-distance>, <mirp>, <mdrp>, and <move> (only when a "relative-to" point is present). This vector lasts only until a new projection vector is set; then it gets canceled.

One or both points in the line may be in the twilight zone. See the explanation for <set-vectors>.

Instructions that store vectors

<store-projection-vector>
<store-freedom-vector>

These instructions store a vector as two numbers, an x-component and a y-component. The x-component and y-component attributes, if given, must be identifiers for variables:

  <store-projection-vector x-component="vx" y-component="vy"/>

If variables are not given, a warning is printed and the values are left on the stack, where they will be picked up correctly by a following set instruction. For example, this code sets the projection vector to be the same as the freedom vector:

  <store-freedom-vector/>
  <set-projection-vector/>

Note that a with block will not pick up the components of a vector from the stack.

Attributes

x-component
The x-component of the vector. Both the x-component and the y-component must be present if either is present; otherwise the one that is present is ignored, and the two components of the vector are left on the stack.
y-component
The y-component of the vector.