592 lines
44 KiB
HTML
592 lines
44 KiB
HTML
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
|
|||
|
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"><html xmlns="http://www.w3.org/1999/xhtml"><head><meta http-equiv="Content-Type" content="text/html; charset=utf-8" /><title>
|
|||
|
RoboThon 2006: Interpolation
|
|||
|
</title>
|
|||
|
<link href="../default.css" type="text/css" rel="stylesheet" />
|
|||
|
<link href="../code/robothon06/py2html.css" type="text/css" rel="stylesheet" />
|
|||
|
</head><body>
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
<script type="text/javascript" src="http://www.google-analytics.com/urchin.js"></script>
|
|||
|
<script type="text/javascript">
|
|||
|
_uacct = "UA-2044310-2";
|
|||
|
urchinTracker();
|
|||
|
</script>
|
|||
|
|
|||
|
<div id="modellogo">
|
|||
|
<img src="../img/drawmodel_header.jpg" width="595" height="112" />
|
|||
|
</div>
|
|||
|
<div class="leftcontent">
|
|||
|
<h1 class="crb-seealso">
|
|||
|
RoboFab
|
|||
|
</h1>
|
|||
|
<p class="menu">
|
|||
|
<a href="../index.html">
|
|||
|
Home
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../download/index.html">
|
|||
|
Download v1.1.1
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../intro.html">
|
|||
|
Intro
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../install.html">
|
|||
|
Install Notes
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../history.html">
|
|||
|
History
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../executive.html">
|
|||
|
Summary
|
|||
|
</a>
|
|||
|
</p>
|
|||
|
|
|||
|
<p class="menu">
|
|||
|
<a href="../howto/index.html">
|
|||
|
How to's
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="index.html">
|
|||
|
Step by step
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../tools/dialogs.html">
|
|||
|
Fab Dialogs
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../objects/index.html">
|
|||
|
Object reference
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../objects/model.html">
|
|||
|
Object map
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../tools/index.html">
|
|||
|
Tools
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../ufo/index.html">
|
|||
|
UFO Overview
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../ufo/specification.html">
|
|||
|
UFO Spec
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../limitations.html">
|
|||
|
Fab Limitations
|
|||
|
</a>
|
|||
|
|
|||
|
<a href="../links/index.html">
|
|||
|
Links
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../credits.html">
|
|||
|
Credits
|
|||
|
</a>
|
|||
|
</p>
|
|||
|
|
|||
|
<h1 class="crb-seealso">
|
|||
|
Support RoboFab
|
|||
|
</h1>
|
|||
|
|
|||
|
|
|||
|
<form action="https://www.paypal.com/cgi-bin/webscr" method="post">
|
|||
|
<input type="hidden" name="cmd" value="_s-xclick">
|
|||
|
<input type="image" src="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" border="0" name="submit" alt="Make payments with PayPal - it's fast, free and secure!">
|
|||
|
<img alt="" border="0" src="https://www.paypal.com/en_US/i/scr/pixel.gif" width="1" height="1">
|
|||
|
<input type="hidden" name="encrypted" value="-----BEGIN PKCS7-----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-----END PKCS7-----
|
|||
|
">
|
|||
|
</form>
|
|||
|
|
|||
|
|
|||
|
|
|||
|
<h2 class="crb-seealso">
|
|||
|
Up
|
|||
|
</h2>
|
|||
|
|
|||
|
<p class="menu">
|
|||
|
<p class="bonbon_uplink"><a href="index.html">Back to Step by step</a></p>
|
|||
|
</p>
|
|||
|
|
|||
|
<h2 class="crb-seealso">
|
|||
|
See also
|
|||
|
</h2>
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
<p class="menu">
|
|||
|
<a href="../howto/generatefonts.html">Generate Fonts</a><br /><a href="../howto/glyphmath.html">Using Glyph Math</a><br /><a href="../howto/interpolate.html">How to interpolate</a><br /><a href="../howto/usetransformations.html">Using transformations</a><br /><a href="../objects/component.html">RComponent</a><br /><a href="../objects/contour.html">RContour</a><br /><a href="../objects/font.html">RFont</a><br /><a href="../objects/glyph.html">RGlyph</a><br /><a href="../objects/lib.html">RLib</a><br /><a href="../objects/pen.html">Pen objects</a><br /><a href="robofab_session1.html">Font object, Info object</a><br /><a href="robofab_session2.html">Glyph object and Pen object</a><br /><a href="robofab_session3.html">Kerning object and glyph building</a><br />
|
|||
|
</p>
|
|||
|
</div>
|
|||
|
|
|||
|
<div class="footer">
|
|||
|
<a href="../feedback.html">
|
|||
|
Feedback
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
<a href="../map.html">
|
|||
|
Sitemap
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
Please also refer to the
|
|||
|
<a href="../download/license.html">
|
|||
|
Legal
|
|||
|
</a>
|
|||
|
<br />
|
|||
|
Copyright 2003-2006 RoboFab
|
|||
|
<br />
|
|||
|
version 1.1.1
|
|||
|
</div>
|
|||
|
|
|||
|
<div class="google">
|
|||
|
|
|||
|
|
|||
|
<h2>RoboFab Mailinglist</h2>
|
|||
|
<p>
|
|||
|
Join the RoboFab users community at Google groups.
|
|||
|
</p>
|
|||
|
|
|||
|
|
|||
|
<img src="http://groups.google.com/groups/img/3nb/groups_bar.gif" alt="Google Groups" height="26" width="132" />
|
|||
|
|
|||
|
<p>
|
|||
|
<form action="http://groups.google.com/group/robofab/boxsubscribe">
|
|||
|
Email: <input type="text" name="../email" />
|
|||
|
<input type="submit" name="../sub" value="Subscribe" />
|
|||
|
</form>
|
|||
|
</p>
|
|||
|
<p>
|
|||
|
<a href="http://groups.google.com/group/robofab">Visit this group</a>
|
|||
|
</p>
|
|||
|
|
|||
|
|
|||
|
<h2>RoboFab Sponsors</h2>
|
|||
|
|
|||
|
<script type="text/javascript">
|
|||
|
|
|||
|
|
|||
|
google_ad_client = "pub-3703953449723704";
|
|||
|
google_ad_width = 120;
|
|||
|
google_ad_height = 600;
|
|||
|
google_ad_format = "120x600_as";
|
|||
|
google_ad_type = "text_image";
|
|||
|
google_ad_channel ="";
|
|||
|
google_color_border = "336699";
|
|||
|
google_color_bg = "FFFFFF";
|
|||
|
google_color_link = "0000FF";
|
|||
|
google_color_url = "008000";
|
|||
|
google_color_text = "000000";
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
</script>
|
|||
|
|
|||
|
|
|||
|
<script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"></script>
|
|||
|
|
|||
|
|
|||
|
|
|||
|
</div>
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
<div class="content">
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
|
|||
|
<h1>
|
|||
|
Scripting for interpolation
|
|||
|
</h1>
|
|||
|
|
|||
|
|
|||
|
<img src="http://letterror.com/code/robofab/img/ondrawmodel_17.gif" width="140" height="96" />
|
|||
|
|
|||
|
<img src="http://letterror.com/code/robofab/img/ondrawmodel_07.gif" />
|
|||
|
|
|||
|
|
|||
|
<h2>Interpolation</h2>
|
|||
|
<p>
|
|||
|
|
|||
|
In this session we're going to look at scripting and interpolation. Building an interpolation system has 2 phases: <strong>preparing</strong> it and <strong>using</strong> it. Though this isn't necessarily a design / production difference. In the first phase you need to make sure all the data is set up properly, the compatible glyphs in each master, matching contours in each glyph, path directions, start point locations etc. This can be a lot of work, but RoboFab can assist by reporting the problems. The second phase, using the interpolation comes when everything works and rather than look for problems (there shouldn't be any) you just want to generate all the weights as fast as possible and get on with it proofing and other things.
|
|||
|
</p>
|
|||
|
|
|||
|
<h2>Terminology</h2>
|
|||
|
<p>
|
|||
|
The glyphs (or whole fonts) that are used in an interpolation system are usually called <strong>masters</strong>. The <strong>interpolation factor</strong> is a number between 0 and 1. With factor = 0 the result will be identical to the first master (in this case glyph "A"), and as you can probably guess, with factor = 1 the result will match glyph "B". Factor =0.5 means the resulting shape will be exactly between the two masters. The factor can actually also be outside the 0, 1 range - in that case we speak of <strong>extrapolation</strong>. The particular change in a glyph when interpolating from one master to another is called an <strong>axis</strong>.
|
|||
|
</p>
|
|||
|
|
|||
|
|
|||
|
<h2>Why use RoboFab interpolation?</h2>
|
|||
|
<p>
|
|||
|
All the alternatives come with strings attached. FontLab's <strong>Blend</strong> tool forces points in contours which don't match. This is handy if you're looking for a quick fix, but it can more or less destroy your masters. Alternatively you can use the Multiple Master tools, but this requires all of your masters to be in the same file and drawing this way can be tricky. Since interpolation is a useful process in typedesign, and a good candidate for scripting we decided to include solid interpolation support in Robofab.
|
|||
|
</p>
|
|||
|
|
|||
|
<h2>Interpolating glyphs</h2>
|
|||
|
<p>
|
|||
|
In the first example we're going to interpolate two glyphs in the same font. This can be useful in the design stage, for sketching or testing. The result is stored in a third glyph. Note: if you want to run this example in FontLab, open a new, empty font. Use the circle tool to draw one circle in "A", and again in "B". Make sure these are different enough to tell what's going on.
|
|||
|
</p>
|
|||
|
|
|||
|
<div class="pythonsource"><pre># robothon06<br># interpolate two glyphs in the same font<br><span class="py_res">from</span> <span class="py_key">robofab</span>.<span class="py_key">world</span> <span class="py_res">import</span> <span class="py_key">CurrentFont</span><br><span class="py_key">f</span> = <span class="py_key">CurrentFont</span>()<br><span class="py_key">factor</span> = <span class="py_num">0.5</span><br><span class="py_key">f</span>[<span class="py_str">"C"</span>].<span class="py_key">interpolate</span>(<span class="py_key">factor</span>, <span class="py_key">f</span>[<span class="py_str">"A"</span>], <span class="py_key">f</span>[<span class="py_str">"B"</span>])<br><span class="py_key">f</span>[<span class="py_str">"C"</span>].<span class="py_key">update</span>()<br></pre></div><div class="pythonsourcetitle"><a href="examples/interpolateGlyphs.py" target="new">download examples/interpolateGlyphs.py</a></div>
|
|||
|
|
|||
|
<p>
|
|||
|
You see there are 3 glyphs involved: the two masters (<strong>"A"</strong> and <strong>"B"</strong>) and a new glyph which is used to store the results. In this case the new glyph is stored as <strong>"C"</strong>, but it can be helpful to give it a more descriptive name. This is not very PostScript-like, but chances are these glyphs won't make it to production anyway, so it's not a problem. Notice that <strong>interpolate()</strong> is a method of the <strong>Glyph</strong> object. The <strong>Font</strong> object has an interpolate method as well, more about that later. The <a href="http://letterror.com/code/robofab/howto/interpolate.html" class="reference" target="docs">obligatory link</a> to the relevant RoboFab documentation.
|
|||
|
</p>
|
|||
|
|
|||
|
<p>
|
|||
|
Here's the same script, but now it generates a range of interpolated glyphs, each with a better name which tells you which interpolation factor was used:
|
|||
|
</p>
|
|||
|
|
|||
|
<div class="pythonsource"><pre># robothon06<br># interpolate two glyphs in the same font a bunch of times<br><span class="py_res">from</span> <span class="py_key">robofab</span>.<span class="py_key">world</span> <span class="py_res">import</span> <span class="py_key">CurrentFont</span><br><span class="py_key">f</span> = <span class="py_key">CurrentFont</span>()<br><span class="py_res">for</span> <span class="py_key">i</span> <span class="py_res">in</span> <span class="py_key">range</span>(<span class="py_num">0</span>, <span class="py_num">10</span>):<br> <span class="py_key">factor</span> = <span class="py_key">i</span>*<span class="py_num">.1</span><br> <span class="py_key">name</span> = <span class="py_str">"result_%f"</span>%<span class="py_key">factor</span><br> <span class="py_res">print</span> <span class="py_str">"interpolating"</span>, <span class="py_key">name</span><br> <span class="py_key">f</span>[<span class="py_key">name</span>].<span class="py_key">interpolate</span>(<span class="py_key">factor</span>, <span class="py_key">f</span>[<span class="py_str">"A"</span>], <span class="py_key">f</span>[<span class="py_str">"B"</span>])<br><span class="py_key">f</span>.<span class="py_key">update</span>()</pre></div><div class="pythonsourcetitle"><a href="examples/interpolateSeries.py" target="new">download examples/interpolateSeries.py</a></div>
|
|||
|
|
|||
|
<div class="pythonoutput"><pre><span class="py_key">interpolating</span> <span class="py_key">result_0</span><span class="py_num">.000000</span><br><span class="py_key">interpolating</span> <span class="py_key">result_0</span><span class="py_num">.100000</span><br><span class="py_key">interpolating</span> <span class="py_key">result_0</span><span class="py_num">.200000</span><br><span class="py_key">interpolating</span> <span class="py_key">result_0</span><span class="py_num">.300000</span><br><span class="py_key">interpolating</span> <span class="py_key">result_0</span><span class="py_num">.400000</span><br><span class="py_key">interpolating</span> <span class="py_key">result_0</span><span class="py_num">.500000</span><br><span class="py_key">interpolating</span> <span class="py_key">result_0</span><span class="py_num">.600000</span><br><span class="py_key">interpolating</span> <span class="py_key">result_0</span><span class="py_num">.700000</span><br><span class="py_key">interpolating</span> <span class="py_key">result_0</span><span class="py_num">.800000</span><br><span class="py_key">interpolating</span> <span class="py_key">result_0</span><span class="py_num">.900000</span></pre></div>
|
|||
|
|
|||
|
<img src="glyphinterpol.gif" alt="" width="493" height="65" />
|
|||
|
|
|||
|
<p>
|
|||
|
Here you see a range of resulting glyphs as they could be generated by the script above.
|
|||
|
</p>
|
|||
|
|
|||
|
<h2>Rounding errors</h2>
|
|||
|
<p>
|
|||
|
When you interpolate in FontLab you need to take into account that the results will be rounded off. Coordinates can only consist of whole numbers, i,e, "101" or "102" but not "101.3290" There is a nice solution for working with floating point precision glyphs using RoboFab. Here's a brief introduction:</p>
|
|||
|
|
|||
|
<div class="pythonsource"><pre># robothon06
<br>
<br><span class="py_res">from</span> <span class="py_key">robofab</span>.<span class="py_key">world</span> <span class="py_res">import</span> <span class="py_key">CurrentFont</span>
<br># We need to import a class with a different
<br># implementation for the glyph object.
<br># It looks a bit odd, but this is how it is done
<br><span class="py_res">from</span> <span class="py_key">robofab</span>.<span class="py_key">objects</span>.<span class="py_key">objectsRF</span> <span class="py_res">import</span> <span class="py_key">RGlyph</span> <span class="py_key">as</span> <span class="py_key">_RGlyph</span>
<br>
<br><span class="py_key">f</span> = <span class="py_key">CurrentFont</span>()
<br>
<br># pick two compatible glyphs as masters
<br><span class="py_key">m1</span> = <span class="py_key">f</span>[<span class="py_str">"A"</span>]
<br><span class="py_key">m2</span> = <span class="py_key">f</span>[<span class="py_str">"B"</span>]
<br>
<br># make a new glyph object from this other glyph class
<br><span class="py_key">g</span> = <span class="py_key">_RGlyph</span>()
<br>
<br># interpolation factor which is bound to make floats
<br><span class="py_key">oddFactor</span> = <span class="py_num">0.2382345</span>
<br>
<br># go!
<br><span class="py_key">g</span>.<span class="py_key">interpolate</span>(<span class="py_key">oddFactor</span>, <span class="py_key">m1</span>, <span class="py_key">m2</span>)
<br>
<br># let's have a look at the raw results
<br><span class="py_res">for</span> <span class="py_key">contour</span> <span class="py_res">in</span> <span class="py_key">g</span>:
<br> <span class="py_res">for</span> <span class="py_key">pt</span> <span class="py_res">in</span> <span class="py_key">contour</span>.<span class="py_key">points</span>:
<br> <span class="py_res">print</span> <span class="py_str">"float"</span>, <span class="py_key">pt</span>.<span class="py_key">x</span>, <span class="py_key">pt</span>.<span class="py_key">y</span>
<br>
<br># a glyph can round itself off:
<br><span class="py_key">g</span>.<span class="py_key">round</span>()
<br>
<br># and then it looks like integers again
<br><span class="py_res">for</span> <span class="py_key">contour</span> <span class="py_res">in</span> <span class="py_key">g</span>:
<br> <span class="py_res">for</span> <span class="py_key">pt</span> <span class="py_res">in</span> <span class="py_key">contour</span>.<span class="py_key">points</span>:
<br> <span class="py_res">print</span> <span class="py_str">"integer"</span>, <span class="py_key">pt</span>.<span class="py_key">x</span>, <span class="py_key">pt</span>.<span class="py_key">y</span>
<br><span class="py_com"> |