Illustrator CS5.1でSVGを書き出す際、オブジェクトの不透明度を9%以下にして小数点以下の桁数を1にすると指数表記になってしまう問題とその対処法

Adobe Illustratorでこのような図を作ってみました。
円を100個配置して、左上から順に不透明度をそれぞれ1%から100%まで設定したもの。

Illustrator上ではこうなるわけですが、これをSVGに書き出してみると

なぜか上段の不透明度1%〜9%の円は半透明になっていませんね。


Google chrome(26.0.1410.64 m)でのスクリーンショット

……という不具合を見つけたので、その理由と対処法を探ってみました。
(ちなみに、手元にあるIllustratorは CS5.1 しかないので、他のバージョンでの動作は未検証です。CS6で直っているといいんですけれども。)

再現条件

この動作が起きる条件は

  1. Adobe Illustratorでオブジェクトの不透明度を9%〜1%にする
  2. ファイル形式はSVG
  3. その際「小数点以下の桁数」を「1」に設定して保存

です。


Illustratorの不透明度とSVGスタイルシート

Illustratorでは不透明度は不透明度は100%から0%で調整できますが、SVGではそれを1から0までの数値で指定します。
具体的にはIllustratorで不透明度が53%の場合、SVGではopacityプロパティ*1の値は0.53となります。では不具合が出ている部分はどのようになっているかというと……

<circle style="opacity:0.1;fill:#0062DF;stroke:#FF471F; <!--(略)-->
<circle style="opacity:9.000000e-002;fill:#0062DF;stroke:#FF471F; <!--(略)-->

上のcircle要素はstyle属性で指定されているopacityプロパティの数値は0.1で、つまり不透明度が10%ということ。これは適切な指定です。
しかし、後段の不透明度9%のはずのopacityプロパティの指定は「9.000000e-002」となぜか指数表記なってしまいます。

指数表記とは

指数表記とはなにか?というのは、詳しくはWikipediaを参考にしてほしいのですが
指数表記 - Wikipedia
要するにこのような感じになっています。
9.000000 \times 10^{-2} = 0.09
つまり「9.000000e-002」は「9.000000 に 10の-2乗(0.01)をかけた数」となります。表記はややこしいですが結果 0.09 という値になるため、全くのでたらめな文字列ではなく不透明度9%を示す指示としてはある意味間違ってはいないです。
ですが、SVGで使われるスタイルシートの数値として指数表記は定義されていません。

参考リンク

そのため指数表記を数値として解釈できず、このような表示になってしまうわけです。


というわけで明らかに Adobe Illustrator CS5.1 のバグなので、Adobe社に不具合報告フォームから通報済みです。



そして対応策

不具合はあるとして、じゃあそれへの対応策はどのようにすればいいでしょうか?

小数点以下の桁数の見直し

最も簡単なのは、SVGに書き出す際に「小数点以下の桁数」を1以外にすることです。


この設定は1〜7までの整数で設定できます。ただあまり数が多いと全体のファイルサイズが必要以上に大きくなってしまうため(参考)、2から3程度で良いでしょう。

CSSプロパティの見直し

もう一つは「CSSプロパティ」を「プレゼンテーション属性」にすることでしょうか。

この設定であれば、不透明度の設定はopacity属性で指定されることになります。

<circle opacity="9.000000e-002" fill="#0062DF" stroke="#FF471F" stroke-miterlimit="10" cx="292.4" cy="39.9" r="13.8"/>

この場合上述のスタイルシートとは異なり、SVGの属性の数値の指定ならば指数表記が定義されているため「9.000000e-002」も有効な値として解釈されます。

(プレゼンテーション属性での出力例)

参考リンク

ですのでここでは指数表記は適切に適用され、不透明度は意図した通りになるわけです。

テキストエディタなどで直接編集

また、もう一つの解決策としては単純に単位を書き換えるのも手ですね。SVGXMLでもあるわけですから、テキストエディタで簡単に値を置換・編集できるのも特徴です。
その際は「0.09」などに書き換えてもいいですが、「.09」といった省略の表記も利用できるのでこうすると少しでも全体のファイルサイズを小さくできるというテクニックもあります*2




指数表記になるパターン

作例の通り、Illustrator上で不透明度が9%〜1%の場合に指数表記になります。0%はオッケー。

不透明度 Illustrator - opacity 本来の値
0% 0 0
1% 1.000000e-002 0.01
2% 2.000000e-002 0.02
3% 3.000000e-002 0.03
4% 4.000000e-002 0.04
5% 5.000000e-002 0.05
6% 6.000000e-002 0.06
7% 7.000000e-002 0.07
8% 8.000000e-002 0.08
9% 9.000000e-002 0.09
10% 0.1 0.1
11% 0.11 0.11



上段でも書いたのですが、手元の環境はCS5.1しかないためCS6ではこの不具合が直っているのか気になるところ……。

><

*1:スタイル属性・スタイル要素の場合

*2:ほんのわずかのファイルサイズ削減ですが