OSDN Git Service

90cccd7946f437cd1fd78c0e4e9d6734e7d6d3e8
[luatex-ja/luatexja.git] / src / addons / luatexja-fontspec-24.sty
1 %
2 % luatexja-fontspec-24.sty
3 %
4
5 \NeedsTeXFormat{LaTeX2e}
6 \ProvidesPackage{luatexja-fontspec-24}[2014/10/29 fontspec support of LuaTeX-ja]
7 \RequirePackage{l3keys2e,luatexja}
8 \ExplSyntaxOn
9
10 %%%%%%%% Change Japanese font family by \rmfamily or not
11 \bool_if:NTF  \ltj_fontspec_match
12 {
13   \renewcommand\jttdefault{\gtdefault}
14   \DeclareRobustCommand\rmfamily
15   {\not@math@alphabet\rmfamily\mathrm
16      \romanfamily\rmdefault\kanjifamily\mcdefault\selectfont}
17   \DeclareRobustCommand\sffamily
18   {\not@math@alphabet\sffamily\mathsf
19      \romanfamily\sfdefault\kanjifamily\gtdefault\selectfont}
20   \DeclareRobustCommand\ttfamily
21   {\not@math@alphabet\ttfamily\mathtt
22      \romanfamily\ttdefault\kanjifamily\jttdefault\selectfont}
23   \DeclareDocumentCommand \setmonojfont { O{} m } {
24     \ltj_fontspec_set_family:Nnn \jttdefault {#1}{#2}
25     \normalfont
26   }
27 }{
28 }
29
30 %%%%%%%% Messages
31
32 \msg_new:nnn {luatexja-fontspec} {addjfontfeatures-ignored}
33 {
34   \string\addjfontfeature (s)~ ignored;\\
35   it~ cannot~ be~ used~ with~ a~ font~ that~ wasn't~ selected~ by~ luatexja-fontspec.
36 }
37
38 \msg_new:nnn {luatexja-fontspec} {altfont-ignored-by-norange}
39 {
40   ignored~ sublist~ `#1'~ in~ AltFont~ (no~ range~ is~ specified).
41 }
42
43 \msg_new:nnn {luatexja-fontspec} {altfont-ignored-by-rangeonly}
44 {
45   ignored~ sublist~ `#1'~ in~ AltFont~ (only~ range~ is~ specified).
46 }
47
48 \cs_generate_variant:Nn \prg_new_conditional:Nnn {Nnx}
49
50 %%%%%%%% \g_ltj_fontspec_scale_fp
51 %% Default scale value for jfont.
52 \fp_new:N \g_ltj_fontspec_scale_fp
53 \group_begin:
54 \fontsize{10}{10}\selectfont
55 \fp_gset:Nn \g_ltj_fontspec_scale_fp {\zw / 10}
56 \group_end:
57
58 %%%%%%%% Internal control sequences
59 %% Each CS is ltj_fontspec version that corresponds to original CS of fontspec.
60 \cs_new:Nn \ltj_fontspec_define_option:nn {
61   \__fontspec_keys_define_code:nnn {fontspec} {#1} {#2}
62 }
63
64 \cs_new:Nn \ltj_fontspec_define_preparse_external:nn {
65   \__fontspec_keys_define_code:nnn {fontspec-preparse-external} {#1} {#2}
66 }
67 \cs_new:Nn \ltj_fontspec_define_altfont_option:nn {
68   \__fontspec_keys_define_code:nnn {fontspec-ltjaltfont} {#1} {#2}
69 }
70
71 %% Alternate Fonts
72 %% Spec: AltFont = {
73 %%   ...
74 %%   { Range = <range>, <font features> },
75 %%   { Range = <range>, Font = <font name>, <font features> },
76 %%   { Range = <range>, Font = <font name> },
77 %%   ...
78 %% }
79 \tl_new:N  \l_ltj_fontspec_altname_tl
80 \tl_new:N  \l_ltj_fontspec_altrange_tl
81 \clist_new:N  \l_ltj_fontspec_altfont_clist
82 \clist_new:N  \l_ltj_fontspec_altfont_leftover_clist
83 \int_new:N \g_ltj_fontspec_altnumber_int
84
85 \ltj_fontspec_define_altfont_option:nn {Range} {
86   \tl_set:Nn \l_ltj_fontspec_altrange_tl {#1}
87 }
88 \ltj_fontspec_define_altfont_option:nn {Font} {
89   \fontspec_complete_fontname:Nn \l_ltj_fontspec_altname_tl {#1}
90 }
91 \__fontspec_keys_define_code:nnn {fontspec-ltjaltfont-reparse} {AltFont} {
92   \clist_put_right:Nn \l_ltj_fontspec_altfont_clist  { #1 }
93 }
94 \__fontspec_keys_define_code:nnn {fontspec-ltjaltfont-reparse} {YokoFeatures} {
95   \clist_put_right:Nn \l_ltj_fontspec_fontfeat_yoko_clist { #1 }
96 }
97 \__fontspec_keys_define_code:nnn {fontspec-ltjaltfont-reparse} {TateFeatures} {
98   \clist_put_right:Nn \l_ltj_fontspec_fontfeat_tate_clist { #1 }
99 }
100 \__fontspec_keys_define_code:nnn {fontspec-ltjaltfont-reparse} {TateFont} {
101   \tl_if_empty:nF {#1} {
102     \fontspec_complete_fontname:Nn \l_ltj_fontspec_fontname_tate_tl {#1}
103   }
104 }
105 %%
106 \clist_new:N \l_ltj_fontspec_fontfeat_yoko_clist
107 \clist_new:N \l_ltj_fontspec_fontfeat_tate_clist
108 \tl_new:N    \l_ltj_fontspec_fontname_tate_tl
109
110 \cs_new:Npn \ltj_fontspec_DeclareFontFamily #1 #2 #3 {
111   \DeclareKanjiFamily {JY3} {#2} {#3}
112   \DeclareKanjiFamily {JT3} {#2} {#3}
113 }
114
115 \cs_set_eq:NN \__ltj_orig_fontspec_select:nn \fontspec_select:nn
116 \cs_new:Nn \ltj_fontspec_select:nn {
117   \group_begin:
118   \ltj_fontspec_define_option:nn {AltFont} {
119     \clist_put_right:Nn \l_ltj_fontspec_altfont_clist  {##1}
120   }
121   \ltj_fontspec_define_option:nn {CID} {
122     \__fontspec_update_featstr:n {cid=##1}
123   }
124   \ltj_fontspec_define_option:nn {JFM} {
125     \__fontspec_update_featstr:n {jfm=##1}
126   }
127   % vary by shape
128   \ltj_fontspec_define_option:nn {YokoFeatures} {
129     \clist_put_right:Nn \l_ltj_fontspec_fontfeat_yoko_clist { ##1 }
130   }
131   \ltj_fontspec_define_option:nn {TateFeatures} {
132     \clist_put_right:Nn \l_ltj_fontspec_fontfeat_tate_clist { ##1 }
133   }
134   \ltj_fontspec_define_option:nn {TateFont}
135   {
136     \tl_if_empty:nF {##1} {
137       \fontspec_complete_fontname:Nn \l_ltj_fontspec_fontname_tate_tl {##1}
138     }
139   }
140   \ltj_fontspec_define_option:nn {JFM-var} {
141     \__fontspec_update_featstr:n {jfmvar=##1}
142   }
143   \ltj_fontspec_define_preparse_external:nn {NoEmbed} {
144     \cs_set:Nn \__fontspec_namewrap:n {psft:####1}
145   }
146   %% Omit the warning message
147   %% "OpenType feature 'Kerning=Off' (-kern) not available ..."
148   \ltj_fontspec_define_option:nn {Kerning/Off} {
149     \__fontspec_update_featstr:n {-kern}
150   }
151   \clist_set:Nx \g__fontspec_default_fontopts_clist {
152     YokoFeatures = { JFM=ujis }, TateFeatures = { JFM=ujisv },
153     Scale=\fp_use:N \g_ltj_fontspec_scale_fp, Kerning=Off,
154     \g__ltj_fontspec_default_fontopts_clist
155   }
156   \prop_set_eq:NN \g__fontspec_fontopts_prop \g__ltj_fontspec_fontopts_prop
157   \cs_set_eq:NN \__fontspec_make_font_shapes:Nnnnn \ltj_fontspec_make_font_shapes:Nnnnn
158   \cs_set_eq:NN \DeclareFontFamily \ltj_fontspec_DeclareFontFamily
159   \tl_set:Nn \g_fontspec_encoding_tl {JY3}
160   \__ltj_orig_fontspec_select:nn{#1}{#2}
161   \group_end:
162 }
163
164 %% declare_shape
165
166 \cs_new:Nn \ltj_fontspec_declare_shape_yoko:nnnn {
167   \ltj_fontspec_declare_shape_aux:nnnnnn {#1} {#2} {#3} {#4} { JY3 } { \l_ltj_fontspec_fontfeat_yoko_clist }
168 }
169 \cs_new:Nn \ltj_fontspec_declare_shape_tate:nnnn {
170   \ltj_fontspec_declare_shape_aux:nnnnnn {#1} {#2} {#3} {#4} { JT3 } { \l_ltj_fontspec_fontfeat_tate_clist }
171 }
172 \cs_new:Nn \ltj_fontspec_declare_shape:nnnn {
173   \ltj_fontspec_declare_shape_yoko:nnnn {#1} {#2} {#3} {#4}
174   \ltj_fontspec_declare_shape_tate:nnnn {#1} {#2} {#3} {#4}
175 }
176 \cs_generate_variant:Nn \ltj_fontspec_declare_shape:nnnn {nnxx}
177 \cs_generate_variant:Nn \ltj_fontspec_declare_shape_yoko:nnnn {nnxx}
178 \cs_generate_variant:Nn \ltj_fontspec_declare_shape_tate:nnnn {nnxx}
179
180 \cs_new:Nn \ltj_fontspec_declare_shape_aux:nnnnnn
181  {
182   \tl_clear:N \l__fontspec_nfss_tl
183   \tl_clear:N \l__fontspec_nfss_sc_tl
184   \tl_set_eq:NN \l__fontspec_saved_fontname_tl \l_fontspec_fontname_tl
185
186   \tl_set:Nn \g_fontspec_encoding_tl {#5}
187   \exp_args:Nx \clist_map_inline:nn {#4}
188    {
189     \tl_clear:N \l__fontspec_size_tl
190     \tl_set_eq:NN \l__fontspec_sizedfont_tl \l__fontspec_saved_fontname_tl % in case not spec'ed
191
192     \keys_set_known:nxN {fontspec-sizing} { \exp_after:wN \use:n ##1 }
193       \l__fontspec_sizing_leftover_clist
194     \tl_if_empty:NT \l__fontspec_size_tl { \__fontspec_error:n {no-size-info} }
195
196     \str_if_eq:nnTF { #5 } { JY3 } {
197       % "normal"
198       \__fontspec_load_fontname:n {\l__fontspec_sizedfont_tl}
199     } {
200       \tl_if_empty:NTF \l_ltj_fontspec_fontname_tate_tl
201         { \__fontspec_load_fontname:n {\l__fontspec_sizedfont_tl} }
202         { \__fontspec_load_fontname:n {\l_ltj_fontspec_fontname_tate_tl} }
203     }
204     \__fontspec_setup_nfss:Nnn \l__fontspec_nfss_tl {#3} {#6}
205    }
206   \bool_set_true:N \l__fontspec_nosc_bool
207   \__fontspec_declare_shapes_normal:nn  {#1} {#2}
208   \__fontspec_declare_shape_slanted:nn  {#1} {#2}
209  }
210
211 \cs_new:Nn \ltj_fontspec_set_family:Nnn {
212   \cs_set_eq:NN \fontspec_select:nn \ltj_fontspec_select:nn
213   \__ltj_orig_fontspec_set_family:Nnn #1 {#2} {#3}
214   \cs_set_eq:NN \fontspec_select:nn \__ltj_orig_fontspec_select:nn
215 }
216 \cs_set_eq:NN \__ltj_orig_fontspec_set_family:Nnn \fontspec_set_family:Nnn
217 \cs_set_eq:NN \__ltj_orig_fontspec_make_font_shapes:Nnnnn \__fontspec_make_font_shapes:Nnnnn
218 \cs_set_eq:NN \__ltj_fontspec_orig_DeclareFontShape \DeclareFontShape
219 \cs_new:Nn \ltj_fontspec_make_font_shapes:Nnnnn {
220   \group_begin:
221     %% 基底フォント
222     \cs_set_eq:NN \__fontspec_font_set:Nnn \use_none:nnn
223     \cs_set_eq:NN \__fontspec_font_if_null:NT \use_none:nn
224     \cs_set_eq:NN \__fontspec_declare_shape:nnxx \ltj_fontspec_declare_shape:nnxx
225     \__ltj_orig_fontspec_make_font_shapes:Nnnnn {#1} {#2} {#3} {#4} {#5}
226     %%
227     \ltj_fontspec_make_font_shapes_alt:Nnnnnn {#1}{#2}{#3}
228      {#4, \l_ltj_fontspec_fontfeat_yoko_clist}{#5} {JY3 }
229     \ltj_fontspec_make_font_shapes_alt:Nnnnnn {#1}{#2}{#3}
230      {#4, \l_ltj_fontspec_fontfeat_tate_clist}{#5} {JT3}
231   \group_end:
232  }
233
234 %%% Altfont 内部処理部
235 \cs_new:Nn \ltj_fontspec_make_font_shapes_alt:Nnnnnn {
236   \group_begin:
237     \str_if_eq:nnTF { #6 } { JY3 } {
238       \cs_set_eq:NN \__fontspec_declare_shape:nnxx \ltj_fontspec_declare_shape_yoko:nnxx
239     }{
240       \cs_set_eq:NN \__fontspec_declare_shape:nnxx \ltj_fontspec_declare_shape_tate:nnxx
241     }
242     \keys_set_known:nn {fontspec-ltjaltfont-reparse} { #4 }
243     \clist_if_empty:NF \l_ltj_fontspec_altfont_clist {
244       \int_gzero:N \g_ltj_fontspec_altnumber_int
245       \clist_map_inline:Nn \l_ltj_fontspec_altfont_clist {
246         \tl_clear:N  \l_ltj_fontspec_altrange_tl
247         \tl_set:Nn \l_ltj_fontspec_altname_tl { #1 }
248         \tl_set:Nn \l_tmpa_tl { #1 }
249
250         \keys_set_known:nxN {fontspec-ltjaltfont} { \exp_after:wN \use:n ##1 }
251           \l_ltj_fontspec_altfont_leftover_clist
252         \keys_set_known:nn {fontspec-ltjaltfont-reparse} { \exp_after:wN \use:n ##1 }
253
254         \tl_if_empty:NT \l_ltj_fontspec_altrange_tl {
255           \msg_warning:nnn  {luatexja-fontspec} {altfont-ignored-by-norange} { ##1 }
256         } {
257           \bool_if:nTF {
258             \tl_if_eq_p:NN \l_ltj_fontspec_altname_tl \l_tmpa_tl
259             &&
260             \tl_if_empty_p:N \l_ltj_fontspec_altfont_leftover_clist
261           } {
262             \msg_warning:nnn  {luatexja-fontspec} {altfont-ignored-by-rangeonly} { ##1 }
263           } {
264             \__ltj_orig_fontspec_make_font_shapes:Nnnnn
265                 { \l_ltj_fontspec_altname_tl } {#2}
266                 {#3 _ alt \int_use:N \g_ltj_fontspec_altnumber_int }
267                 {#4, \l_ltj_fontspec_altfont_leftover_clist }
268                 {#5}
269             \DeclareAlternateKanjiFont
270               { #6 }{ \l_fontspec_family_tl }{#2}{#3}%
271               { #6 }{ \l_fontspec_family_tl }{#2}
272               { #3 _alt \int_use:N \g_ltj_fontspec_altnumber_int }
273               { \l_ltj_fontspec_altrange_tl }
274             \int_gincr:N \g_ltj_fontspec_altnumber_int
275           }
276         }
277       }
278     }
279   \group_end:
280 }
281
282
283 %%%%%%%% User commands
284 \DeclareDocumentCommand \jfontspec { O{} m O{} } {
285   \ltj_fontspec_set_family:Nnn \k@family {#1,#3}{#2}
286   \selectfont
287   \ignorespaces
288 }
289
290 \DeclareDocumentCommand \setmainjfont { O{} m O{} } {
291   \ltj_fontspec_set_family:Nnn \mcdefault {#1,#3}{#2}
292   \DeclareSymbolFont{mincho}{JY3}{\l_fontspec_family_tl}{m}{n}
293   \SetSymbolFont{mincho}{bold}{JY3}{\l_fontspec_family_tl}{bx}{n}
294   \normalfont
295 }
296
297 \DeclareDocumentCommand \setsansjfont { O{} m O{} } {
298   \ltj_fontspec_set_family:Nnn \gtdefault {#1,#3}{#2}
299   \DeclareMathAlphabet{\mathgt}{JY3}{\l_fontspec_family_tl}{m}{n}
300   \normalfont
301 }
302
303 \DeclareDocumentCommand \newjfontfamily { m O{} m O{} } {
304   \cs_set_eq:NN \fontspec_set_family:Nnn \ltj_fontspec_set_family:Nnn
305   \newfontfamily #1 [#2] {#3} [#4]
306   \cs_set_eq:NN \fontspec_set_family:Nnn \__ltj_orig_fontspec_set_family:Nnn
307 }
308
309 \DeclareDocumentCommand \newjfontface { m O{} m O{} } {
310   \newjfontfamily #1 [ BoldFont={},ItalicFont={},SmallCapsFont={},#2,#4 ] {#3}
311 }
312
313 \clist_new:N \g__ltj_fontspec_default_fontopts_clist
314 \prop_new:N \g__ltj_fontspec_fontopts_prop
315 \DeclareDocumentCommand \defaultjfontfeatures { t+ o m }
316  {
317   \IfNoValueTF {#2}
318    { \__ltj_fontspec_set_default_features:nn {#1} {#3} }
319    { \__ltj_fontspec_set_font_default_features:nnn {#1} {#2} {#3} }
320   \ignorespaces
321  }
322 \cs_new:Nn \__ltj_fontspec_set_default_features:nn
323  {
324    \clist_set_eq:NN \l__ltj_fontspec_tmp_clist \g__fontspec_default_fontopts_clist
325    \clist_set_eq:NN \g__fontspec_default_fontopts_clist \g__ltj_fontspec_default_fontopts_clist
326    \__fontspec_set_default_features:nn {#1} {#2}
327    \clist_set_eq:NN \g__ltj_fontspec_default_fontopts_clist \g__fontspec_default_fontopts_clist
328    \clist_set_eq:NN \g__fontspec_default_fontopts_clist \l__ltj_fontspec_tmp_clist
329  }
330 \cs_new:Nn \__ltj_fontspec_set_font_default_features:nnn
331  {
332    \prop_set_eq:NN \l__ltj_fontspec_tmp_prop \g__fontspec_fontopts_prop
333    \prop_set_eq:NN \g__fontspec_fontopts_prop \g__ltj_fontspec_fontopts_prop
334    \__fontspec_set_font_default_features:nnn {#1} {#2} {#3}
335    \prop_set_eq:NN \g__ltj_fontspec_fontopts_prop \g__fontspec_fontopts_prop
336    \prop_set_eq:NN \g__fontspec_fontopts_prop \l__ltj_fontspec_tmp_prop
337  }
338
339 \DeclareDocumentCommand \addjfontfeatures {m} {
340   \ltj_fontspec_if_fontspec_font:TF
341    {
342     \group_begin:
343       \tl_set_eq:NN \f@family \k@family
344       \cs_set_eq:NN \fontspec_select:nn \ltj_fontspec_select:nn
345       \addfontfeatures {#1}
346     \group_end:
347     \fontfamily\l_fontspec_family_tl\selectfont
348    }{
349     \msg_warning:nn  {luatexja-fontspec} {addjfontfeatures-ignored}
350    }
351   \ignorespaces
352 }
353
354 \cs_set_eq:NN \addjfontfeature \addjfontfeatures
355
356 \prg_new_conditional:Nnn \ltj_fontspec_if_fontspec_font: {TF,T,F}
357 {
358   \cs_if_exist:cTF {g__fontspec_ \k@family _prop} \prg_return_true: \prg_return_false:
359 }
360
361 %%% CJKShape=JIS2004
362 \__fontspec_define_feature_option:nnnnn{CJKShape}{JIS2004}{20}{100}{+jp04}
363 %%% CharacterWidth={VerticalAlternateProportional, VerticalAlternateHalf}
364 \__fontspec_define_feature_option:nnnnn{CharacterWidth}{VerticalAlternateProportional}{22}{100}{+vpal}
365 \__fontspec_define_feature_option:nnnnn{CharacterWidth}{VerticalAlternateHalf}{22}{101}{+vhal}
366 \__fontspec_define_feature_option:nnnnn{Kerning}{Vertical}       {}{}{+vkrn}
367
368
369 \ExplSyntaxOff
370 %%%%%%%% Now we completely ignore kanjifont definition file.
371 \@ltj@use@fdfalse
372
373 % We must redefine \try@load@fontshape to ignore kanjifont definitions at all.
374 \def\try@load@fontshape{%
375    \expandafter
376    \ifx\csname \f@encoding+\f@family\endcsname\relax
377        \directlua{luatexja.jfont.is_kenc('\luatexluaescapestring{\f@encoding}')}%
378 \ifin@\else % Alphabetic font
379     \@font@info{Try loading font information for \f@encoding+\f@family}%
380     \global\expandafter\let
381        \csname\f@encoding+\f@family\endcsname\@empty
382      \nfss@catcodes
383      \let\nfss@catcodes\relax
384      \edef\reserved@a{%
385        \lowercase{%
386          \noexpand\InputIfFileExists{\f@encoding\f@family.fd}}}%
387      \reserved@a\relax
388           {\@input@{\f@encoding\f@family.fd}}%
389 \fi
390    \fi}
391
392 \endinput