版本記錄
版本號(hào) | 時(shí)間 |
---|---|
V1.0 | 2017.10.22 |
前言
Core Text
框架主要用來做文字處理讽营,是的iOS3.2+
和OSX10.5+
中的文本引擎蝗砾,讓您精細(xì)的控制文本布局和格式踢俄。它位于在UIKit
中和CoreGraphics/Quartz
之間的最佳點(diǎn)但金。接下來這幾篇我們就主要解析該框架褂微。感興趣的可以前面幾篇友题。
1. Core Text框架詳細(xì)解析(一) —— 基本概覽
2. Core Text框架詳細(xì)解析(二) —— 關(guān)于Core Text
3. Core Text框架詳細(xì)解析(三) —— Core Text總體概覽
4. Core Text框架詳細(xì)解析(四) —— Core Text文本布局操作
字體操作
本章介紹一些常見的字體處理操作嗤堰,并顯示如何使用Core Text進(jìn)行編碼。 這些操作在iOS和OS X上是相同的。本章包含以下代碼列表操作:
- Creating Font Descriptors
- Creating a Font from a Font Descriptor
- Creating Related Fonts
- Serializing a Font
- Creating a Font from Serialized Data
- Changing Kerning
- Getting Glyphs for Characters
Creating Font Descriptors - 創(chuàng)建字體描述符
Listing 3-1
中的示例函數(shù)從指定PostScript
字體名稱和點(diǎn)大小的參數(shù)值創(chuàng)建一個(gè)字體描述符踢匣。
// Listing 3-1 Creating a font descriptor from a name and point size
CTFontDescriptorRef CreateFontDescriptorFromName(CFStringRef postScriptName,
CGFloat size)
{
return CTFontDescriptorCreateWithNameAndSize(postScriptName, size);
}
Listing 3-2
中的示例函數(shù)從字體系列名稱和字體特征中創(chuàng)建一個(gè)字體描述符告匠。
// Listing 3-2 Creating a font descriptor from a family and traits
NSString* familyName = @"Papyrus";
CTFontSymbolicTraits symbolicTraits = kCTFontTraitCondensed;
CGFloat size = 24.0;
NSMutableDictionary* attributes = [NSMutableDictionary dictionary];
[attributes setObject:familyName forKey:(id)kCTFontFamilyNameAttribute];
// The attributes dictionary contains another dictionary, the traits dictionary,
// which in this example specifies only the symbolic traits.
NSMutableDictionary* traits = [NSMutableDictionary dictionary];
[traits setObject:[NSNumber numberWithUnsignedInt:symbolicTraits]
forKey:(id)kCTFontSymbolicTrait];
[attributes setObject:traits forKey:(id)kCTFontTraitsAttribute];
[attributes setObject:[NSNumber numberWithFloat:size]
forKey:(id)kCTFontSizeAttribute];
CTFontDescriptorRef descriptor =
CTFontDescriptorCreateWithAttributes((CFDictionaryRef)attributes);
CFRelease(descriptor);
Creating a Font from a Font Descriptor - 從字體描述符創(chuàng)建字體
Listing 3-3 顯示了如何創(chuàng)建一個(gè)字體描述符并使用它來創(chuàng)建一個(gè)字體。 當(dāng)您調(diào)用CTFontCreateWithFontDescriptor時(shí)离唬,通常會(huì)為矩陣參數(shù)傳遞NULL
后专,以指定默認(rèn)(identity)
矩陣。 CTFontCreateWithFontDescriptor的大小和矩陣(第二和第三個(gè))參數(shù)將覆蓋字體描述符中指定的任何內(nèi)容输莺,除非它們未指定(大小為0.0戚哎,矩陣為NULL)。
// Listing 3-3 Creating a font from a font descriptor
NSDictionary *fontAttributes =
[NSDictionary dictionaryWithObjectsAndKeys:
@"Courier", (NSString *)kCTFontFamilyNameAttribute,
@"Bold", (NSString *)kCTFontStyleNameAttribute,
[NSNumber numberWithFloat:16.0],
(NSString *)kCTFontSizeAttribute,
nil];
// Create a descriptor.
CTFontDescriptorRef descriptor =
CTFontDescriptorCreateWithAttributes((CFDictionaryRef)fontAttributes);
// Create a font using the descriptor.
CTFontRef font = CTFontCreateWithFontDescriptor(descriptor, 0.0, NULL);
CFRelease(descriptor);
Creating Related Fonts - 創(chuàng)建相關(guān)字體
將現(xiàn)有字體轉(zhuǎn)換為相關(guān)或相似的字體通常很有用嫂用。 Listing 3-4 中的示例函數(shù)顯示了如何使用函數(shù)調(diào)用傳遞的布爾參數(shù)的值使粗體或粗體字體粗體顯示型凳。 如果當(dāng)前的字體系列沒有請(qǐng)求的樣式,則該函數(shù)返回NULL嘱函。
// Listing 3-4 Changing traits of a font
CTFontRef CreateBoldFont(CTFontRef font, Boolean makeBold)
{
CTFontSymbolicTraits desiredTrait = 0;
CTFontSymbolicTraits traitMask;
// If requesting that the font be bold, set the desired trait
// to be bold.
if (makeBold) desiredTrait = kCTFontBoldTrait;
// Mask off the bold trait to indicate that it is the only trait
// to be modified. As CTFontSymbolicTraits is a bit field,
// could change multiple traits if desired.
traitMask = kCTFontBoldTrait;
// Create a copy of the original font with the masked trait set to the
// desired value. If the font family does not have the appropriate style,
// returns NULL.
return CTFontCreateCopyWithSymbolicTraits(font, 0.0, NULL, desiredTrait, traitMask);
}
Listing 3-5
中的示例函數(shù)將給定字體轉(zhuǎn)換為另一個(gè)字體系列中的類似字體甘畅,如果可能,將保留特征往弓。 它可能返回NULL疏唾。 傳遞大小參數(shù)為0.0和矩陣參數(shù)為NULL以保留原始字體的大小。
// Listing 3-5 Converting a font to another family
CTFontRef CreateFontConvertedToFamily(CTFontRef font, CFStringRef family)
{
// Create a copy of the original font with the new family. This call
// attempts to preserve traits, and may return NULL if that is not possible.
// Pass in 0.0 and NULL for size and matrix to preserve the values from
// the original font.
return CTFontCreateCopyWithFamily(font, 0.0, NULL, family);
}
Serializing a Font - 序列化字體
Listing 3-6
中的示例函數(shù)顯示了如何創(chuàng)建XML數(shù)據(jù)以序列化可以嵌入到文檔中的字體函似。 或者荸实,并且優(yōu)選地,可以使用NSArchiver
缴淋。 這只是完成此任務(wù)的一種方法,但它會(huì)保留以后重新創(chuàng)建確切字體所需字體的所有數(shù)據(jù)泄朴。
// Listing 3-6 Serializing a font
CFDataRef CreateFlattenedFontData(CTFontRef font)
{
CFDataRef result = NULL;
CTFontDescriptorRef descriptor;
CFDictionaryRef attributes;
// Get the font descriptor for the font.
descriptor = CTFontCopyFontDescriptor(font);
if (descriptor != NULL) {
// Get the font attributes from the descriptor. This should be enough
// information to recreate the descriptor and the font later.
attributes = CTFontDescriptorCopyAttributes(descriptor);
if (attributes != NULL) {
// If attributes are a valid property list, directly flatten
// the property list. Otherwise we may need to analyze the attributes
// and remove or manually convert them to serializable forms.
// This is left as an exercise for the reader.
if (CFPropertyListIsValid(attributes, kCFPropertyListXMLFormat_v1_0)) {
result = CFPropertyListCreateXMLData(kCFAllocatorDefault, attributes);
}
}
}
return result;
}
Creating a Font from Serialized Data - 從序列化數(shù)據(jù)中創(chuàng)建字體
Listing 3-7
中的示例函數(shù)顯示了如何從展平的XML數(shù)據(jù)創(chuàng)建字體引用重抖。 它顯示如何折疊字體屬性并利用這些屬性創(chuàng)建字體。
// Listing 3-7 Creating a font from serialized data
CTFontRef CreateFontFromFlattenedFontData(CFDataRef iData)
{
CTFontRef font = NULL;
CFDictionaryRef attributes;
CTFontDescriptorRef descriptor;
// Create our font attributes from the property list.
// For simplicity, this example creates an immutable object.
// If you needed to massage or convert certain attributes
// from their serializable form to the Core Text usable form,
// do it here.
attributes =
(CFDictionaryRef)CFPropertyListCreateFromXMLData(
kCFAllocatorDefault,
iData, kCFPropertyListImmutable, NULL);
if (attributes != NULL) {
// Create the font descriptor from the attributes.
descriptor = CTFontDescriptorCreateWithAttributes(attributes);
if (descriptor != NULL) {
// Create the font from the font descriptor. This sample uses
// 0.0 and NULL for the size and matrix parameters. This
// causes the font to be created with the size and/or matrix
// that exist in the descriptor, if present. Otherwise default
// values are used.
font = CTFontCreateWithFontDescriptor(descriptor, 0.0, NULL);
}
}
return font;
}
Changing Kerning - 改變字距
默認(rèn)情況下啟用連接和字距調(diào)整祖灰。 如果要禁用钟沛,請(qǐng)將kCTKernAttributeName
屬性設(shè)置為0。Listing 3-8將前幾個(gè)字符的kern
大小設(shè)置為很大的數(shù)字局扶。
// Listing 3-8 Setting kerning
// Set the color of the first 13 characters to red
// using a previously defined red CGColor object.
CFAttributedStringSetAttribute(attrString, CFRangeMake(0, 13),
kCTForegroundColorAttributeName, red);
// Set kerning between the first 18 chars to be 20
CGFloat otherNum = 20;
CFNumberRef otherCFNum = CFNumberCreate(NULL, kCFNumberCGFloatType, &otherNum);
CFAttributedStringSetAttribute(attrString, CFRangeMake(0,18),
kCTKernAttributeName, otherCFNum);
Getting Glyphs for Characters - 獲取字符的字形
Listing 3-9
顯示了如何使用單個(gè)字體獲取字符串中的字符的字形恨统。 大多數(shù)時(shí)候你應(yīng)該只使用一個(gè)CTLine
對(duì)象獲取這個(gè)信息,因?yàn)橐粋€(gè)字體可能不會(huì)對(duì)整個(gè)字符串進(jìn)行編碼三妈。 此外畜埋,簡(jiǎn)單的字符到字形映射將無法獲得復(fù)雜腳本的正確外觀。 如果您嘗試為字體顯示特定的Unicode字符畴蒲,則這種簡(jiǎn)單的字形映射可能是適當(dāng)?shù)摹?/p>
Listing 3-9 Getting glyphs for characters
void GetGlyphsForCharacters(CTFontRef font, CFStringRef string)
{
// Get the string length.
CFIndex count = CFStringGetLength(string);
// Allocate our buffers for characters and glyphs.
UniChar *characters = (UniChar *)malloc(sizeof(UniChar) * count);
CGGlyph *glyphs = (CGGlyph *)malloc(sizeof(CGGlyph) * count);
// Get the characters from the string.
CFStringGetCharacters(string, CFRangeMake(0, count), characters);
// Get the glyphs for the characters.
CTFontGetGlyphsForCharacters(font, characters, glyphs, count);
// Do something with the glyphs here. Characters not mapped by this font will be zero.
// ...
// Free the buffers
free(characters);
free(glyphs);
}
后記
未完悠鞍,待續(xù)~~~