Размытые UILabel как программная подпредставление UITableViewCell contentView - PullRequest
20 голосов
/ 12 января 2010

Я добавляю экземпляр UILabel в качестве подпредставления моего пользовательского UITableViewCell экземпляра contentView.

Когда я выбираю ячейку, строка выделяется синим цветом, за исключением фона метки. Текст на этикетке четкий.

Когда я устанавливаю для свойства backgroundColor метки и содержимого [UIColor clearColor], текст метки становится размытым.

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

Одно предложение, которое я читал в другом месте, касалось round значений метки frame, но это не имело никакого эффекта.

КОД

Вот фрагмент моего пользовательского UITableViewCell метода -setNeedsLayout подпредставления:

UILabel *_objectTitleLabel = [[UILabel alloc] initWithFrame:CGRectNull];
_objectTitleLabel.text = [self.awsObject cleanedKey];
_objectTitleLabel.font = [UIAppDelegate defaultObjectLabelFont];
_objectTitleLabel.highlightedTextColor = [UIColor clearColor]; //[UIAppDelegate defaultLabelShadowTint];
_objectTitleLabel.backgroundColor = [UIColor clearColor]; //[UIAppDelegate defaultWidgetBackgroundTint];
_objectTitleLabel.frame = CGRectMake(
        kCellImageViewWidth + 2.0 * self.indentationWidth,
        0.5 * (self.tableView.rowHeight - 1.5 * kCellLabelHeight) + kCellTitleYPositionNudge,
        contentViewWidth,
        kCellLabelHeight
);
_objectTitleLabel.frame = CGRectIntegral(_objectTitleLabel.frame);
_objectTitleLabel.tag = kObjectTableViewCellTitleSubviewType;
//NSLog(@"_objectTitleLabel: %@", NSStringFromCGRect(_objectTitleLabel.frame));
[self.contentView addSubview:_objectTitleLabel];
[_objectTitleLabel release], _objectTitleLabel = nil;

...

self.contentView.backgroundColor = [UIAppDelegate defaultWidgetBackgroundTint]; 
self.contentView.clearsContextBeforeDrawing = YES;
self.contentView.autoresizesSubviews = YES;
self.contentView.clipsToBounds = YES;
self.contentView.contentMode = UIViewContentModeRedraw;

Ответы [ 9 ]

35 голосов
/ 23 января 2010

Проблема заключается в субпиксельном рендеринге, который возникает, когда ваш источник (который является значением с плавающей точкой) имеет ненулевой дробный компонент. Округлите до ближайшего целого числа и все будет в порядке.

9 голосов
/ 14 мая 2013

В моем случае, установив shouldRasterize = YES на CGLayer представления, содержащего UILabel, был виновником. Удаление этой строки сделало текст красивым и четким.

7 голосов
/ 29 марта 2010

Хорошо, обнаружена проблема. Убедитесь, что координаты родительского вида также округлены.

2 голосов
/ 06 сентября 2013

Установка shouldRasterize на YES может привести к размытости. Установите масштаб растеризации, и это должно устранить размытость. [self.layer setRasterizationScale:[[UIScreen mainScreen] scale]];

2 голосов
/ 18 сентября 2010

Другой причиной искаженного / размытого текста является повторное использование ячеек. Если вы выводите из очереди многократно используемую ячейку, она может перерисовываться с другими размерами где-то еще и снова использоваться, когда попадает в вашу ячейку с искаженным текстом.

Чтобы обеспечить уникальность ячеек, обязательно выделите новую ячейку для указателей, где текст искажен, и отметьте этот экземпляр UITableViewCell с другим идентификатором повторного использования. Конечно, это практично, если вы имеете дело с очень небольшим количеством ячеек и точно знаете, какие ячейки вызывают проблемы.

2 голосов
/ 22 января 2010

Я сам столкнулся с этой проблемой сегодня и где-то читал, что нецелые значения для источника и размера фрейма UILabel могут вызвать это (я знаю, что они являются числами с плавающей точкой, но вы знаете, что я имею в виду). Должно быть более элегантное решение, но этот быстрый взлом, похоже, решил проблему для меня:

self.valueLabel.frame = CGRectMake((int) frame.origin.x, (int) frame.origin.y, (int) frame.size.width, (int) frame.size.height);

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

1 голос
/ 22 августа 2010

Вызывается ли -setNeedsLayout даже для удаленных многоразовых ячеек? Если это так, в ячейку уже будет добавлена ​​метка к представлению содержимого, и вы нарисуете ее дважды, делая ее размытой. Вы можете решить эту проблему неэффективно, удалив все подпредставления представления содержимого перед добавлением подпредставления:

for (UIView *subview in [[self contentView] subviews]) {
     [subview removeFromSuperview];
}

Лучшим решением было бы предоставить свойства подкласса вашей ячейки, чтобы позволить вам изменять содержимое повторно используемой ячейки по мере необходимости, а не восстанавливать ее иерархию представления с нуля.

1 голос
/ 30 мая 2010

Используйте раунд (); Функции C предоставляются по причине.

#define roundCGRectValues (frame) \
frame = CGRectMake(round(frame.origin.x),round(frame.origin.y),round(frame.size.width),round(frame.size.height));

Все, что вам нужно.

1 голос
/ 22 января 2010

Иногда причиной размытости, которую вы упомянули, может быть то, что рамка меток находится за рамкой ячейки. Даже если вы видите весь текст, который вы поместили внутри метки в своей ячейке, фактический размер метки может быть больше, чем размер рамки ячейки.

Чтобы проверить, является ли это причиной эффекта, который вы видите, я бы посоветовал проверить / распечатать все данные о размере / местоположении меток после его создания, а затем проверить в методе делегата tableView: heightForRowAtIndexPath: что это подходит в высоту клетки вы возвращаетесь за клетку. Надеюсь, это поможет в вашем случае.

...