試験運用中なLinux備忘録・旧記事

はてなダイアリーで公開していた2007年5月-2015年3月の記事を保存しています。

日本語を名前に含むフォントをWineのフォント置換に使用するための変換をPythonで行う

(2015/1/11)infファイルを使用せずに非対話的にレジストリの操作を行う」などの要領で直接CP932のエンコーディングでフォント名を指定してレジストリファイルを適用すればよいため、本記事の方法で内部の名前を取得する必要はない。コードもPython 2向けで古いが、このままとする。以下、以前の内容となる。


Wineのフォント置換では、システム上の認識されているフォント一覧である「Software\\Microsoft\\Windows NT\\CurrentVersion\\Fonts」(${WINEPREFIX}/system.reg内)を見ても分かるように、フォント名に日本語が含まれる場合には、Unicodeのコードによる表記が使用される。
一方、Pythonという言語もまた、文字列をUnicodeで扱うことができる(Unicode文字列)。例として、

#! /usr/bin/python
# -*- encoding: utf-8 -*-

name = u"IPA Pゴシック"
print repr(name)

上のコードを実行すると

u'IPA P\u30b4\u30b7\u30c3\u30af'

という出力が得られる。
このフォント名に関して、(Wine上で扱われる名前の表記として)先述の「Software\\Microsoft\\Windows NT\\CurrentVersion\\Fonts」では

"IPA P\x30b4\x30b7\x30c3\x30af (TrueType)"="[ipagp.ttfの場所(Windows形式)]"

のようになっているため、コードの番号部分(「30b4 30b7 30c3 30af」=「ゴ シ ッ ク」)は一致している。

つまり、PythonUnicode文字列とrepr()関数をうまく使うことで、Wineで日本語を含む名前のフォントを置換したいとき、レジストリに指定する名前(の表記)を得るために使える。

作成したのは下のコード。
[任意]ファイル名: winefontname.py

#! /usr/bin/python
# -*- encoding: utf-8 -*-

import sys

def winefontname(name_utf8):
  try:
    exec "name = u\"%s\"" % name_utf8.decode("utf-8")
  except SyntaxError:
    return "(error)"
  code = repr(name)  # 「"%r" % name」でも同様
  return code.replace("\\u", "\\x")[2:-1]

def print_name(name_utf8):
  print "'%s' => '%s'" % (name_utf8, winefontname(name_utf8))


names = sys.argv[1:]

if len(names) >= 1:
  for name in names:
    print_name(u"%s".encode("utf-8") % name)
else:
  print "使用法: %s [フォント名...]" % __file__

下は使用例。

$ winefontname.py "IPA Pゴシック" "MS Pゴシック"
'IPA Pゴシック' => 'IPA P\x30b4\x30b7\x30c3\x30af'
'MS Pゴシック' => '\xff2d\xff33 \xff30\x30b4\x30b7\x30c3\x30af'

(2008/6/22)引数の処理を修正