Размер шрифта для дисплея Retina

Мое приложение для Mac OS рисует текст, используя такой код:

void drawString(NSString* stringToDraw)
{
    NSFontManager *fontManager = [NSFontManager sharedFontManager];
    NSString* fontName =  [NSString stringWithCString: "Helvetica" encoding: NSMacOSRomanStringEncoding];
    NSFont* font = [fontManager fontWithFamily:fontName traits:0 weight:5 size:9];
    NSMutableDictionary *attribs = [[NSMutableDictionary alloc] init];
    [attribs setObject:font forKey:NSFontAttributeName];
    [stringToDraw drawAtPoint:NSMakePoint (0, 0) withAttributes:attribs];
}

Поскольку рисование текста — это очень небольшая часть приложения, этот простой подход до сих пор работал хорошо. Но теперь, с новым дисплеем Retina, пользователи жалуются, что текст кажется слишком большим по сравнению с остальной графикой. Кажется, что указание абсолютного размера шрифта (в моем случае 9) больше не работает.

Как я могу исправить этот код, чтобы он хорошо работал как для дисплеев Retina, так и для дисплеев без Retina?


person Periodic Maintenance    schedule 12.08.2012    source источник


Ответы (1)


Размер шрифта измеряется в пунктах, а не в пикселях. Поэтому любое значение не должно зависеть от разрешения Retina. Например, этот код работает нормально:

- (void)drawRect:(NSRect)dirtyRect
{
    CGRect textRect = CGRectInset(self.bounds, 15.0, 15.0);

    [[[NSColor whiteColor] colorWithAlphaComponent:0.5] setFill];
    NSRectFillUsingOperation(textRect, NSCompositeSourceOver);

    NSFont *font = [[NSFontManager sharedFontManager] fontWithFamily:@"Helvetica"
                                                              traits:0.0
                                                              weight:5.0
                                                                size:30.0];
    [@"Hello\nWorld" drawInRect:textRect
                 withAttributes:@{ NSFontAttributeName : font }];
}

Результаты:

Без сетчатки

Retina

Если у вас есть точные размеры пикселей для разных режимов отображения, попробуйте что-то вроде этого:

CGFloat contentsScale = self.window.backingScaleFactor;
CGFloat fontSize = (contentsScale > 1.0 ? RETINA_FONT_SIZE : STANDARD_FONT_SIZE);
NSFont *font = [[NSFontManager sharedFontManager] fontWithFamily:@"Helvetica"
                                                          traits:0.0
                                                          weight:5.0
                                                            size:fontSize];

Это работает?

person Vadim    schedule 12.08.2012
comment
Я начинаю понимать, в чем моя проблема: поэтому любое значение не должно зависеть от разрешения Retina — мне нужно указать размер текста в пикселях, чтобы он соответствовал исходной графике, которая также основана на пикселях. - person Periodic Maintenance; 13.08.2012
comment
Он работает, хотя и не совсем так, как закодировано выше. У меня нет доступа к окну, поэтому мне пришлось вызывать backingScaleFactor для главного экрана. Также я работаю под SDK 10.6, поэтому backingScaleFactor доступен только через вызов NSInvocation. Однако основная идея работает, и я приму ответ. БЛАГОДАРНОСТЬ! - person Periodic Maintenance; 14.08.2012