diff options
Diffstat (limited to 'Resource/Init/gs_fapi.ps')
-rw-r--r-- | Resource/Init/gs_fapi.ps | 463 |
1 files changed, 463 insertions, 0 deletions
diff --git a/Resource/Init/gs_fapi.ps b/Resource/Init/gs_fapi.ps new file mode 100644 index 00000000..1ca3dff7 --- /dev/null +++ b/Resource/Init/gs_fapi.ps @@ -0,0 +1,463 @@ +% Copyright (C) 2001-2019 Artifex Software, Inc. +% All Rights Reserved. +% +% This software is provided AS-IS with no warranty, either express or +% implied. +% +% This software is distributed under license and may not be copied, +% modified or distributed except as expressly authorized under the terms +% of the license contained in the file LICENSE in this distribution. +% +% Refer to licensing information at http://www.artifex.com or contact +% Artifex Software, Inc., 1305 Grant Avenue - Suite 200, Novato, +% CA 94945, U.S.A., +1(415)492-9861, for further information. +% + +% Redefine Font and CIDFont categories with FAPI-handeled fonts. + +systemdict /.FAPIavailable known { //null .FAPIavailable } { //false } ifelse not { + (%END FAPI) .skipeof +} if + +languagelevel 2 .setlanguagelevel + +%==================================================================== +% Redefine Font category with FAPIfontmap and CIDFont with FAPIfontmap : +15 dict begin % a temporary dictionary for local binding. + +/EmbedFontObjectsQuery mark + /.EmbedFontObjects 0 +.dicttomark def + +/is_device_compatible_to_FAPI % - is_device_compatible_to_FAPI <bool> +{ + //true % removed a bogus check against EmbedFontObjectsQuery + % + % Temporary switch to allow override of FAPI and fallback to GS font rendering + % to be removed at some date after FT integration is completed and released. + % + /DisableFAPI where { + /DisableFAPI get not and + }if + % The code above assumes that only the requested parameter is rendered. + % The commented-out code below may be useful for general case. + % Keeping it for a while. + % counttomark 2 idiv { + % exch /.EmbedFontObjects eq { + % counttomark 1 add 1 roll cleartomark + % 0 eq exit + % } if + % } repeat + % dup mark eq { + % pop //true + % } if +} bind def + +%----------------------------- Process FAPIconfig ----------------------- + +% The HookDiskFonts and HookEmbeddedFonts take a simple array setting normally. +% but if two or more FAPI plugins are built in, they can take a dictionary, +% whose contents are the FAPI subtype string of a given plugin as the key, +% and an array containing the (sub)set of font types the plugin should handle. +% Any repetition of font types is ill advised since the resulting bevhaviour +% will depend on the order entries are stored in the dictionary, which is +% indeterminate. An attempt to use request a font scaler/renderer which cannot +% deal with a given font type will result in the FAPI resorting to it's default +% search for a viable plugin. +% +% As an example, you might want UFST to handle Truetype/Type 42 fonts, and +% Freetype to handle others, thus: +% /HookDiskFonts << /UFST [11 42] /FreeType [1 2 9] >> +% /HookEmbeddedFonts << /UFST [11 42] /FreeType [1 2 9] >> + +/Config +<< + % If we've got a FAPIConfig, run it now. + systemdict /FAPIconfig known + { + /FAPIconfig .systemvar .runlibfile + } if + + % Now setup defaults for any entries not set above - these defaults are correct + % for FAPI/Freeetype + currentdict /FontPath known not { /FontPath (/Fonts)} if % A default directory for FAPI-handled font files + % path in FAPIfontmap. + currentdict /CIDFontPath known not { /CIDFontPath (/CIDFonts)} if % A default directory for FAPI-handled CIDfont % files path in FAPIcidfmap. + currentdict /HookDiskFonts known not { /HookDiskFonts [1 2 9 11 42] } if % FontType values for disk PS fonts to be + % redirected to FAPI. + currentdict /HookEmbeddedFonts known not { /HookEmbeddedFonts [1 2 9 11 42] } if % FontType values for embedded PS fonts to be + % redirected to FAPI. + /ServerOptions 2 dict +>> def +systemdict /.FAPIconfig //Config put + +/UFST .FAPIavailable +{ + systemdict /UFST_SSdir known + { + /UFSTFONTDIR UFST_SSdir def + systemdict /UFST_SSdir undef + } + { + /UFSTROMFONTDIR (%rom%fontdata/) def + + UFSTROMFONTDIR (mtfonts/pcl45/mt3/plug__xi.fco) + concatstrings status + { + pop pop pop pop + /UFSTFONTDIR UFSTROMFONTDIR def + } + { + /UFSTFONTDIR () def + } ifelse + } ifelse + + systemdict /UFST_PlugIn known not + { + systemdict /UFST_PlugIn UFSTFONTDIR (mtfonts/pcl45/mt3/plug__xi.fco) concatstrings put + } if + + systemdict /FCOfontfile known not + { + systemdict /FCOfontfile UFSTFONTDIR (mtfonts/pclps2/mt3/pclp2_xj.fco) concatstrings put + } if + + systemdict /FCOfontfile2 known not + { + systemdict /FCOfontfile2 UFSTFONTDIR (mtfonts/pcl45/mt3/wd____xh.fco) concatstrings put + } if + + systemdict /FAPIfontmap known not + { + systemdict /FAPIfontmap (FCOfontmap-PCLPS2) put + } if +} if + +() +systemdict /UFST_SSdir .knownget { + (UFST_SSdir=) exch concatstrings concatstrings +} if +systemdict /UFST_PlugIn .knownget { + 1 index length 0 ne { + exch .filenamelistseparator concatstrings exch + } if + (UFST_PlugIn=) exch concatstrings concatstrings +} if +dup length 0 ne { + //Config /ServerOptions get exch /UFST exch put +} { + pop +} ifelse + +%------------------Copy the FontEmulationProcs here : ------------------- + +/FontEmulationProcs /ProcSet findresource { + def +} forall + +currentdict /super.complete_instance currentdict /complete_instance get put + +%-----------FAPI-specific methods for category redefinition : ----------- + +/RefinePath % <FontDict> /key RefinePath <FontDict> +{ exch begin + //Config exch get + /Path exch + Path //false .file_name_combine not { + exch + (Can't combine paths ) print print ( and ) print = + /RefinePath cvx /configurationerror signalerror + } if + def + currentdict end +} bind def + +/complete_instance % <font_name> <FontDict> <Options> complete_FAPI_Font <font_name> <FontDict> +{ //super.complete_instance exec + dup /CIDFontName known { /CIDFontPath } { /FontPath } ifelse //RefinePath exec +} bind def + +/IsMyRecord % <raw_record> -> <raw_record> bool +{ dup type /dicttype eq { dup /FAPI known } { //false } ifelse +} bind def + +/IsActive % <record> IsActive <bool> +{ pop //is_device_compatible_to_FAPI exec +} bind def + +/FontRecordVirtualMethods //RecordVirtualMethodsStub dup length 2 add dict copy begin + /IsActive //IsActive def + /MakeInstance % <Name> <record> MakeInstance <Name> <Instance> <size> + { currentglobal 3 1 roll //true setglobal + //FontOptions //complete_instance exec + 2 copy //GetSize exec + 4 3 roll setglobal + } bind def +currentdict end def + +/CIDFontRecordVirtualMethods //RecordVirtualMethodsStub dup length 3 add dict copy begin + /GetCSI //TranslateCSI def + /IsActive //IsActive def + /MakeInstance % <Name> <record> MakeInstance <Name> <Instance> <size> + { currentglobal 3 1 roll //true setglobal + //CIDFontOptions //complete_instance exec + 2 copy //GetSize exec + 4 3 roll setglobal + } bind def +currentdict end def + +/ReadFCOfontmap: % <path> ReadFCOfontmap: name dict ... +{ + /fontfile exch def + { + currentfile =string readline not { + pop exit + } if + dup length 0 ne { + 0 () /SubFileDecode filter + dup token not { + % A comment line + closefile + } { + dup /EndFCOfontmap cvx eq { + pop closefile exit + } if + exch dup token not { + /ReadFCOfontmap: cvx /rangecheck signalerror + } if + exch dup token not { + /StandardEncoding + } { + dup type /nametype ne { + /ReadFCOfontmap: cvx /rangecheck signalerror + } if + } ifelse + findencoding + exch dup token not { + //null + } { + dup type /nametype ne { + /ReadFCOfontmap: cvx /rangecheck signalerror + } if + /Decoding findresource + } ifelse + exch closefile % index name enc dec|null + 4 3 roll % name enc dec|null index + << /Path fontfile + /FontType 1 + /FAPI /UFST + /SubfontId counttomark 2 add -1 roll + /Decoding counttomark 2 add -1 roll + dup //null eq { + pop pop + } if + /Encoding counttomark 2 add -1 roll + + /FontInfo + << + /UnderlineThickness 50 + /Weight (Regular) + /version (0.00) + /ItalicAngle 0 + /UnderlinePosition -100 + /FamilyName () + /Notice () + /FullName () + >> + % although we pretend this is a Type 1, the FAPI interface currently + % needs an identity FontMatrix + /FontMatrix [0.001 0.0 0.0 0.001 0.0 0.0] + % we need a fake CharStrings dictionary to placate certain jobs + % which try to look inside it + /CharStrings + << + /.notdef ( ) + StandardEncoding { ( ) } forall + >> + % FontBBox will get replaced with valid numbers pulled from the rendering engine + /FontBBox [-128 -128 1024 1024] cvx + >> % dup { exch == = } forall + } ifelse + } { + pop + } ifelse + } loop + currentdict /fontfile undef +} bind def + +%----------------------------------The Redefintion--------------------- + +/MappedCategoryRedefiner /ProcSet findresource /Redefine get /Redefine exch def + +% Redefine the /Font category : +4 dict begin + /CategoryName /Font def + /MapFileName systemdict /FAPIfontmap known {/FAPIfontmap .systemvar} {(FAPIfontmap)} ifelse def + /VerifyMap { pop } bind def + /PreprocessRecord % <map> <Name> <raw_record> PreprocessRecord <map> <Name> <record> <bool> + { //IsMyRecord exec dup { + pop dup /RecordVirtualMethods //FontRecordVirtualMethods put + //true + } if + } bind def +currentdict end Redefine + +% Redefine the /CIDFont category : +4 dict begin + /CategoryName /CIDFont def + /MapFileName systemdict /FAPIcidfmap known {/FAPIcidfmap .systemvar} {(FAPIcidfmap)} ifelse def + /VerifyMap { pop } bind def + /PreprocessRecord % <map> <Name> <raw_record> PreprocessRecord <map> <Name> <record> <bool> + { //IsMyRecord exec dup { + pop dup /RecordVirtualMethods //CIDFontRecordVirtualMethods put + //true + } if + } bind def +currentdict end Redefine + +%==================== A hook for buildfont* operators ==================== + +% The procedure .FAPIhook redirects PS fonts to FAPI on necessity. +% This depends on the following conditions : +% +% 1. If font dictionary has /FAPI entry, it is a font listed in FAPIconfig.FontPath, +% and must be build with .FAPIrebuildfont, or a copy of a font, which was +% built with .FAPIrebuildfont . +% +% 2. If the font dictionary has /PathLoad entry, and has no /FAPI entry, +% it is an installed PS font, which is described in lib/fontmap or +% in GS_FONTPATH. .loadfont inserts /PathLoad entry for this case +% (see gs_fonts.ps). +% +% Installed fonts are being loaded with GS font loader, +% the they are passed to FAPI is same way as embedded fonts are. +% We do so because UFST cannot read fonts, which don't +% follow Type 1/42 file format strongly. +% +% 3. Executing .loadfont, we place /FAPI_hook_disable in the 0th +% element of some procedure on the execution stack - see gs_fonts.ps . +% If FAPI_hook finds /FAPI_hook_disable in there, +% it knows that it is called for a disk font during +% its internal definefont. +% +% 4. If font dictionary has no /FAPI entry, and has no /Path entry, +% and if we are not in .loadfont context, it is an embedded font. +% +% 5. Two entries to be defined in lib/FAPIconfig to control the hooking of PS fonts : +% HookDiskFonts and HookEmbeddedFonts . +% They specify arrays of font types (integers) to be redirected with FAPI. +% HookDiskFonts controls disk PS fonts (which fall into (2) and (3) ). +% HookEmbeddedFonts controls fonts being embedded into documents. +% +% 7. We apply the operator .passtoFAPI for checking whether FAPI can handle a font. +% If so, we insert /FAPI entry into the font dictionary and convert it +% with .FAPIrebuildfont . Otherwise the font is handled with the native GS font renderer. + +/FAPI_hook_debug % <proc> FAPI_hook_debug - +FAPIDEBUG { {exec} } { {pop} } ifelse +bind def + +/FAPI_hook_warn % <proc> FAPI_hook_debug - +QUIET { {pop} } { {exec} } ifelse +bind def + +/FAPI_is_hook_disabled % - FAPI_is_hook_disabled <bool> +{ % checks whether execution stack contains packedarray started with /FAPI_hook_disable . + /FAPI_hook_disable /MappedCategoryRedefiner /ProcSet findresource /execstack_lookup get exec + //null ne +} bind def + +/FAPIhook_aux % <string|name> <font_dict> .FAPIhook <string|name> <font> +{ % name <<font>> + { (\nFAPIhook ) print 1 index = flush } //FAPI_hook_debug exec + dup /FAPI known { + { //PrintFontRef exec ( is mapped to FAPI=) print dup /FAPI get = flush } //FAPI_hook_debug exec + //true .FAPIrebuildfont //ChooseDecoding exec + } { + dup /PathLoad known dup { + { (PathLoad known for the font ) print //PrintFontRef exec (.\n) print flush} //FAPI_hook_debug exec + } { + pop //FAPI_is_hook_disabled exec dup + { pop + { (FAPIhook is in .loadfont context for the font ) print //PrintFontRef exec (.\n) print flush } //FAPI_hook_debug exec + //true + } if + } ifelse + { /HookDiskFonts } { /HookEmbeddedFonts } ifelse + //Config exch get % name <<font>> [types] + + dup type /dicttype eq + { + //false exch + { + 3 index //GetFontType exec //FindInArray exec + { + 2 index exch /FAPIPlugInReq exch put + pop //true exit + } + { pop } ifelse + } forall + } + { + 1 index //GetFontType exec //FindInArray exec % name <<font>> bHook + } ifelse + + { { (Trying to render the font ) print //PrintFontRef exec ( with FAPI...\n) print flush } //FAPI_hook_debug exec + .FAPIpassfont { + { //PrintFontRef exec ( is being rendered with FAPI=) print dup /FAPI get = flush } //FAPI_hook_debug exec + //false .FAPIrebuildfont //ChooseDecoding exec + } { + { (Can't render ) print //PrintFontRef exec ( with FAPI, will do with native GS renderer.\n) print flush } //FAPI_hook_warn exec + } ifelse + } { + { (The font ) print //PrintFontRef exec ( doesn't need to render with FAPI.\n) print flush } //FAPI_hook_debug exec + } ifelse + + % Remove the plugin request from the font dictionary + dup /FAPIPlugInReq undef + } ifelse +} bind def + +/FAPIhook % <string|name> <font_dict> .FAPIhook <string|name> <font> +{ //is_device_compatible_to_FAPI exec + { //FAPIhook_aux exec + } { + { (FAPIhook is disabled for the current device.\n) print flush } //FAPI_hook_debug exec + } ifelse +} bind def + +% ------------------ Redefine .buildfont* with FAPI : ----------------------- + +/.buildfont1 +{ //.buildfont1 exec //FAPIhook exec +} bind % 'odef' is below. + +/.buildfont2 +{ //.buildfont2 exec //FAPIhook exec +} bind % 'odef' is below. + +/.buildfont42 +{ //.buildfont42 exec //FAPIhook exec +} bind % 'odef' is below. + +/.buildfont9 +{ //.buildfont9 exec //FAPIhook exec +} bind % 'odef' is below. + +/.buildfont10 +{ //.buildfont10 exec //FAPIhook exec +} bind % 'odef' is below. + +/.buildfont11 +{ //.buildfont11 exec //FAPIhook exec +} bind % 'odef' is below. + +end % the temporary dictionary for local binding. +odef odef odef odef odef odef + +% Undef these, not needed outside this file +[ /.FAPIavailable /.FAPIpassfont /.FAPIrebuildfont ] systemdict .undefinternalnames + +.setlanguagelevel + +%END FAPI |