i
[chise/ruby.git] / chise / csf.rb
1 # Copyright (C) 2002-2004 Kouichirou Eto, All rights reserved.
2
3 require "sgl"
4 #require "kconv"
5 #require "uconv"
6 require "chise/iconv"
7 require "chise/config"
8
9 module StrokeFont
10   CSF_FONT_DIR = Config.instance.csf_dir+"/"
11   CSF_DEFAULT_FILE  = "KST32B.CSF1"
12   CSF_KOUKOTSU_FILE = "KST32ZX.CSF1"
13
14   class CSFStrokeMaker
15     DEST_WIDTH = 1000 #\91å\82«\82³\82ð\82¨\82¨\82æ\82»1000x1000\82É\90³\8bK\89»\82·\82é\81B
16     ORG_WIDTH = 32 #\8c³\82Ì\83T\83C\83Y\82Í\81A\89¡30\81~\8fc32
17     def initialize
18       @x, @y, @nx, @ny = 0, 0, 0, 0
19       @strokes = Strokes.new
20     end
21     attr_reader :strokes
22     def move_to_x(x) @x = x; @nx = x; end
23     def draw_to_x(x) @nx = x; drawline; @x = @nx; @y = @ny; end
24     def next_x_to(x) @nx = x; end
25     def move_to_y(y) @y = y; @ny = y; end
26     def draw_to_y(y) @ny = y; drawline; @x = @nx; @y = @ny; end
27     def drawline()
28       @strokes.add_line(t(@x), t(@y), t(@nx), t(@ny))
29     end
30     def t(a) a*DEST_WIDTH/ORG_WIDTH; end
31   end
32
33   class CSFParser
34     def self.parse(str) #Strokes\82ð\95Ô\82·
35       return Strokes.new if str == nil
36       sm = CSFStrokeMaker.new
37       (0...str.length).each {|i|
38         n = str[i]
39         if 0x21 <= n && n <= 0x26
40           sm.move_to_x(n - 0x21)
41         elsif 0x28 <= n && n <= 0x3f
42           sm.move_to_x(n - 0x28 + 6)
43         elsif 0x40 <= n && n <= 0x5b
44           sm.draw_to_x(n - 0x40)
45         elsif 0x5e <= n && n <= 0x5f
46           sm.draw_to_x(n - 0x5e + 28)
47         elsif 0x60 <= n && n <= 0x7d
48           sm.next_x_to(n - 0x60)
49         elsif 0x7e == n
50           sm.move_to_y(n - 0x7e)
51         elsif 0xa1 <= n && n <= 0xbf
52           sm.move_to_y(n - 0xa1 + 1)
53         elsif 0xc0 <= n && n <= 0xdf
54           sm.draw_to_y(n - 0xc0)
55         end
56       }
57       return sm.strokes
58     end
59   end
60
61   class CSFGlyph
62     def initialize(code, stroke)
63       @code = code
64       @stroke_str = stroke
65       @strokes = nil
66     end
67     attr_reader :strokes
68
69     def parse()
70       return if @strokes
71       @strokes = CSFParser.parse(@stroke_str)
72     end
73
74     def init
75       parse if @strokes.nil?
76     end
77   end
78
79   class CSFFont
80     def initialize(file=CSF_DEFAULT_FILE)
81       @file = CSF_FONT_DIR + file
82       @glyphs = []
83       read_file
84       @rend = nil
85       @rend = StrokesRenderer.new
86       @rend.hsv = [50, 100, 100]
87     end
88
89     def read_file()
90       open(@file) {|f|
91         while(line = f.gets)
92           next if line =~ /^\*/
93           c, s = line.split
94           code = c.hex #JIS\82Ì\92l\82ª\90\94\92l\82Å\82Í\82¢\82é
95           @glyphs[code] = CSFGlyph.new(code, s)
96         end
97       }
98     end
99
100     def init(code)
101       glyph = @glyphs[code]
102       return if glyph == nil
103       glyph.init()
104       glyph.parse
105       @rend.set_strokes(glyph.strokes)
106     end
107
108     def draw(code) #\88ø\90\94\82É\82ÍJIS\82ð\90\94\92l\89»\82µ\82½\82à\82Ì\82ª\82Í\82¢\82é
109       glyph = @glyphs[code]
110       return if glyph == nil
111       @rend.draw
112     end
113
114     def print(code)
115       jis = JISX0208.new
116       char = jis.get_char(code)
117       printf("[%s][%04x]\n", char.nil? ? "nil" : char.map_sjis, code)
118     end
119
120     def ucs_to_jis(ucs)
121       char = Character.get(ucs)
122       j = char.japanese_jisx0208
123       return j
124     end
125
126   end
127 end