Rework font configuration to handle the updated (and rather different) .nfont package format.

git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/back/trunk@14556 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
Alexander Malmberg 2002-09-25 20:42:33 +00:00
parent 79ee0fe839
commit dcf402e6b5
2 changed files with 138 additions and 86 deletions

View file

@ -1,3 +1,8 @@
2002-09-25 22:39 Alexander Malmberg <alexander@malmberg.org>
* Source/art/ftfont.m: Rework font configuration code to handle
the updated (and rather different) .nfont package format.
2002-09-24 14:38 Alexander Malmberg <alexander@malmberg.org> 2002-09-24 14:38 Alexander Malmberg <alexander@malmberg.org>
* Source/art/ftfont.m: Use GSFontAntiAlias defaults value to decide * Source/art/ftfont.m: Use GSFontAntiAlias defaults value to decide

View file

@ -30,6 +30,7 @@
#include <Foundation/NSPathUtilities.h> #include <Foundation/NSPathUtilities.h>
#include <Foundation/NSFileManager.h> #include <Foundation/NSFileManager.h>
#include <Foundation/NSUserDefaults.h> #include <Foundation/NSUserDefaults.h>
#include <Foundation/NSBundle.h>
#include <Foundation/NSDebug.h> #include <Foundation/NSDebug.h>
#include <AppKit/GSFontInfo.h> #include <AppKit/GSFontInfo.h>
#include <AppKit/NSAffineTransform.h> #include <AppKit/NSAffineTransform.h>
@ -101,6 +102,10 @@ static NSMutableSet *families_seen, *families_pending;
@public @public
NSString *familyName; NSString *familyName;
/* the following two are localized */
NSString *faceName;
NSString *displayName;
NSArray *files; NSArray *files;
int weight; int weight;
unsigned int traits; unsigned int traits;
@ -122,8 +127,14 @@ static NSMutableSet *families_seen, *families_pending;
-(NSString *) description -(NSString *) description
{ {
return [NSString stringWithFormat: @"<FTFaceInfo %p: %@ %i %i>", return [NSString stringWithFormat: @"<FTFaceInfo %p: '%@' %@ %i %i>",
self, files, weight, traits]; self, displayName, files, weight, traits];
}
/* FTFaceInfo:s should never be deallocated */
-(void) dealloc
{
NSLog(@"Warning: -dealloc called on %@",self);
} }
@end @end
@ -170,6 +181,7 @@ static struct
{@"Nord" ,NSBoldFontMask ,14}, {@"Nord" ,NSBoldFontMask ,14},
{@"Italic" ,NSItalicFontMask ,-1}, {@"Italic" ,NSItalicFontMask ,-1},
{@"Oblique" ,NSItalicFontMask ,-1},
{@"Cond" ,NSCondensedFontMask ,-1}, {@"Cond" ,NSCondensedFontMask ,-1},
{@"Condensed" ,NSCondensedFontMask ,-1}, {@"Condensed" ,NSCondensedFontMask ,-1},
@ -177,13 +189,12 @@ static struct
}; };
int i; int i;
*weight = 5;
*traits = 0; *traits = 0;
// printf("do '%@'\n", s); // printf("do '%@'\n", s);
while ([s length] > 0) while ([s length] > 0)
{ {
// printf(" got '%@'\n", s); // printf(" got '%@'\n", s);
if ([s hasSuffix: @"-"]) if ([s hasSuffix: @"-"] || [s hasSuffix: @" "])
{ {
// printf(" do -\n"); // printf(" do -\n");
s = [s substringToIndex: [s length] - 1]; s = [s substringToIndex: [s length] - 1];
@ -208,79 +219,99 @@ static struct
} }
static void add_face(NSString *family, NSString *face, NSDictionary *d, static void add_face(NSString *family, int family_weight,
NSString *path, BOOL valid_face) unsigned int family_traits, NSDictionary *d, NSString *path,
BOOL from_nfont)
{ {
FTFaceInfo *fi; FTFaceInfo *fi;
int weight; int weight;
unsigned int traits; unsigned int traits;
NSString *full_name;
// printf("'%@'-'%@' |%@|\n", family, face, d); NSString *fontName;
NSString *faceName, *rawFaceName;
if (valid_face)
if (!from_nfont)
{ {
int p; NSLog(@".font not back in yet");
if ([face isEqual: @"Normal"]) return;
full_name = family;
else
full_name = [NSString stringWithFormat: @"%@-%@", family, face];
p = traits_from_string(face, &traits, &weight);
/* if (p > 0)
NSLog(@"failed to split: %@ to %i %04x %i", face, p, traits, weight);
else
NSLog(@"got %04x %i for %@", traits, weight, face);*/
}
else
{
int p = traits_from_string(family, &traits, &weight);
full_name = family;
if (p > 0)
{
face = [family substringFromIndex: p];
family = [family substringToIndex: p];
if ([face length] <= 0)
face = @"Normal";
else
full_name = [NSString stringWithFormat: @"%@-%@", family, face];
}
else
face = @"Normal";
if ([families_seen member: family])
{
// NSLog(@"#2 already seen %@", family);
return;
}
[families_pending addObject: family];
family = [families_pending member: family];
// NSLog(@"split %@ to '%@' '%@' %04x %i", full_name, family, face, traits, weight);
} }
if ([fcfg_allFontNames containsObject: full_name]) fontName = [d objectForKey: @"PostScriptName"];
if (!fontName)
{
NSLog(@"Warning: Face in %@ has no PostScriptName!",path);
return;
}
if ([fcfg_allFontNames containsObject: fontName])
return; return;
fi = [[FTFaceInfo alloc] init]; fi = [[FTFaceInfo alloc] init];
fi->familyName = [family copy];
if ([d objectForKey: @"LocalizedNames"])
{ {
NSArray *files = [d objectForKey: @"Files"]; NSDictionary *l;
int i, c = [files count]; NSArray *lang;
int i;
if (!files) l = [d objectForKey: @"LocalizedNames"];
lang = [NSUserDefaults userLanguages];
faceName = nil;
rawFaceName = [l objectForKey: @"English"];
for (i = 0; i < [lang count] && !faceName; i++)
{ {
NSLog(@"No filename specified for font '%@'!", full_name); faceName = [l objectForKey: [lang objectAtIndex: i]];
DESTROY(fi);
return;
} }
if (!faceName)
fi->files = [[NSMutableArray alloc] init]; faceName = rawFaceName;
for (i = 0; i < c; i++) if (!faceName)
{ {
[(NSMutableArray *)fi->files addObject: faceName = @"<unknown face>";
[path stringByAppendingPathComponent: NSLog(@"Warning: couldn't find localized face name or fallback for %@",fontName);
[files objectAtIndex: i]]];
} }
} }
else if ((faceName = [d objectForKey: @"Name"]))
{
rawFaceName = faceName;
/* TODO: Smarter localization? Parse space separated parts and
translate individually? */
/* TODO: Need to define the strings somewhere, and make sure the
strings files get created. */
faceName = [NSLocalizedStringFromTableInBundle(faceName,nil,
[NSBundle bundleForClass: fi->isa],nil) copy];
fi->faceName = faceName;
}
else
{
NSLog(@"Warning: Can't find name for face %@ in %@!",fontName,path);
return;
}
fi->displayName = [[family stringByAppendingString: @" "]
stringByAppendingString: faceName];
weight = family_weight;
if (rawFaceName)
traits_from_string(rawFaceName, &traits, &weight);
{
NSArray *files = [d objectForKey: @"Files"];
int i, c = [files count];
if (files)
{
fi->files = [[NSMutableArray alloc] init];
for (i = 0; i < c; i++)
{
[(NSMutableArray *)fi->files addObject:
[path stringByAppendingPathComponent:
[files objectAtIndex: i]]];
}
}
}
if ([d objectForKey: @"Weight"]) if ([d objectForKey: @"Weight"])
weight = [[d objectForKey: @"Weight"] intValue]; weight = [[d objectForKey: @"Weight"] intValue];
@ -288,6 +319,7 @@ static void add_face(NSString *family, NSString *face, NSDictionary *d,
if ([d objectForKey: @"Traits"]) if ([d objectForKey: @"Traits"])
traits = [[d objectForKey: @"Traits"] intValue]; traits = [[d objectForKey: @"Traits"] intValue];
traits |= family_traits;
fi->traits = traits; fi->traits = traits;
if ([d objectForKey: @"RenderHints_hack"]) if ([d objectForKey: @"RenderHints_hack"])
@ -300,20 +332,17 @@ static void add_face(NSString *family, NSString *face, NSDictionary *d,
fi->render_hints_hack=0x00202; fi->render_hints_hack=0x00202;
} }
fi->familyName = [family copy]; NSDebugLLog(@"ftfont", @"adding '%@' '%@'", fontName, fi);
NSDebugLLog(@"ftfont", @"adding '%@' '%@'", full_name, fi); [fcfg_all_fonts setObject: fi forKey: fontName];
[fcfg_allFontNames addObject: fontName];
// printf("'%@' fi=|%@|\n", full_name, fi);
[fcfg_all_fonts setObject: fi forKey: full_name];
[fcfg_allFontNames addObject: full_name];
{ {
NSArray *a; NSArray *a;
NSMutableArray *ma; NSMutableArray *ma;
a = [NSArray arrayWithObjects: a = [NSArray arrayWithObjects:
full_name, fontName,
face, faceName,
[NSNumber numberWithInt: weight], [NSNumber numberWithInt: weight],
[NSNumber numberWithUnsignedInt: traits], [NSNumber numberWithUnsignedInt: traits],
nil]; nil];
@ -333,12 +362,13 @@ static void add_face(NSString *family, NSString *face, NSDictionary *d,
static void load_font_configuration(void) static void load_font_configuration(void)
{ {
int i, j, c; int i, j, k, c;
NSArray *paths; NSArray *paths;
NSString *path, *font_path; NSString *path, *font_path;
NSFileManager *fm = [NSFileManager defaultManager]; NSFileManager *fm = [NSFileManager defaultManager];
NSArray *files; NSArray *files;
NSDictionary *d; NSDictionary *d;
NSArray *faces;
fcfg_all_fonts = [[NSMutableDictionary alloc] init]; fcfg_all_fonts = [[NSMutableDictionary alloc] init];
fcfg_allFontFamilies = [[NSMutableDictionary alloc] init]; fcfg_allFontFamilies = [[NSMutableDictionary alloc] init];
@ -352,17 +382,18 @@ static void load_font_configuration(void)
{ {
path = [paths objectAtIndex: i]; path = [paths objectAtIndex: i];
path = [path stringByAppendingPathComponent: @"Fonts"]; path = [path stringByAppendingPathComponent: @"Fonts"];
// printf("try %@\n", path);
files = [fm directoryContentsAtPath: path]; files = [fm directoryContentsAtPath: path];
c = [files count]; c = [files count];
for (j = 0; j < c; j++) for (j = 0; j < c; j++)
{ {
NSString *family, *face; NSString *family;
NSEnumerator *e;
NSDictionary *face_info; NSDictionary *face_info;
NSString *font_info_path; NSString *font_info_path;
int weight;
unsigned int traits;
font_path = [files objectAtIndex: j]; font_path = [files objectAtIndex: j];
if (![[font_path pathExtension] isEqual: @"nfont"]) if (![[font_path pathExtension] isEqual: @"nfont"])
continue; continue;
@ -378,25 +409,39 @@ static void load_font_configuration(void)
font_path = [path stringByAppendingPathComponent: font_path]; font_path = [path stringByAppendingPathComponent: font_path];
NSDebugLLog(@"ftfont",@"loading %@",font_path);
font_info_path = [font_path stringByAppendingPathComponent: @"FontInfo.plist"]; font_info_path = [font_path stringByAppendingPathComponent: @"FontInfo.plist"];
if (![fm fileExistsAtPath: font_info_path]) if (![fm fileExistsAtPath: font_info_path])
continue; continue;
d = [NSDictionary dictionaryWithContentsOfFile: font_info_path]; d = [NSDictionary dictionaryWithContentsOfFile: font_info_path];
if (!d) if (!d)
continue; continue;
d = [d objectForKey: @"Faces"];
e = [d keyEnumerator]; if ([d objectForKey: @"Weight"])
while ((face = [e nextObject])) weight = [[d objectForKey: @"Weight"] intValue];
else
weight = 5;
if ([d objectForKey: @"Traits"])
traits = [[d objectForKey: @"Traits"] intValue];
else
traits = 0;
faces = [d objectForKey: @"Faces"];
if (![faces isKindOfClass: [NSArray class]])
{ {
face_info = [d objectForKey: face]; NSLog(@"Warning: %@ isn't a valid .nfont package, ignoring.",
if ([face_info isKindOfClass: [NSString class]]) font_path);
face_info = [NSArray arrayWithObject: face_info]; if ([faces isKindOfClass: [NSDictionary class]])
if ([face_info isKindOfClass: [NSArray class]]) NSLog(@"(it looks like an old-style .nfont package)");
face_info = [NSDictionary dictionaryWithObject: face_info continue;
forKey: @"Files"]; }
add_face(family, face, face_info, font_path, YES); for (k = 0; k < [faces count]; k++)
{
face_info = [faces objectAtIndex: k];
add_face(family, weight, traits, face_info, font_path, YES);
} }
} }
@ -410,13 +455,14 @@ static void load_font_configuration(void)
family = [font_path stringByDeletingPathExtension]; family = [font_path stringByDeletingPathExtension];
font_path = [path stringByAppendingPathComponent: font_path]; font_path = [path stringByAppendingPathComponent: font_path];
d = [NSDictionary dictionaryWithObject: d = [NSDictionary dictionaryWithObjectsAndKeys:
[NSArray arrayWithObjects: [NSArray arrayWithObjects:
family, family,
[family stringByAppendingPathExtension: @"afm"], [family stringByAppendingPathExtension: @"afm"],
nil] nil],
forKey: @"Files"]; @"Files", /* TODO */
add_face(family, nil, d, font_path, NO); nil];
add_face(family, 5, 0, d, font_path, NO);
} }
[families_seen unionSet: families_pending]; [families_seen unionSet: families_pending];
[families_pending removeAllObjects]; [families_pending removeAllObjects];
@ -509,9 +555,10 @@ static FT_Error ft_get_face(FTC_FaceID fid, FT_Library lib, FT_Pointer data, FT_
font_entry = [fcfg_all_fonts objectForKey: name]; font_entry = [fcfg_all_fonts objectForKey: name];
if (!font_entry) if (!font_entry)
{ {
font_entry = [fcfg_all_fonts objectForKey: [fcfg_allFontNames objectAtIndex: 0]]; NSLog(@"Warning: font '%@' doesn't exist",name);
NSLog(@"Warning: can't find font '%@', falling back to '%@'", name = [fcfg_allFontNames objectAtIndex: 0];
name, [fcfg_allFontNames objectAtIndex: 0]); font_entry = [fcfg_all_fonts objectForKey: name];
NSLog(@"falling back to '%@'",name);
} }
face_info = font_entry; face_info = font_entry;