Ios 如何知道UILabel中的单词是否被剪切
我尝试开发自动收缩功能。我已将文本属性设置为固定大小Ios 如何知道UILabel中的单词是否被剪切,ios,objective-c,Ios,Objective C,我尝试开发自动收缩功能。我已将文本属性设置为固定大小UILabel。之后,我降低字体大小,检查文本是否适合给定的容器大小 问题是UILabel忽略NSLineBreakByWordWrapping,如果一个单词长于容器宽度。导致我有剪尾字 代码如下: - (void) setCardText:(NSString *)txt { NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc]
UILabel
。之后,我降低字体大小,检查文本是否适合给定的容器大小
问题是UILabel
忽略NSLineBreakByWordWrapping
,如果一个单词长于容器宽度。导致我有剪尾字
代码如下:
- (void) setCardText:(NSString *)txt {
NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc] initWithString:txt];
NSMutableParagraphStyle *paragraphStyle = [[NSMutableParagraphStyle alloc] init];
[paragraphStyle setLineBreakMode:NSLineBreakByWordWrapping];
[paragraphStyle setAlignment:NSTextAlignmentCenter];
[attributedString addAttribute:NSParagraphStyleAttributeName value:paragraphStyle range:NSMakeRange(0, [txt length])];
self.cardLabel.attributedText = attributedString;
for (CGFloat fontSize = 40; fontSize >=5; fontSize--) {
[self.cardLabel setFont:[UIFont fontWithName:@"GothamPro-Light" size:fontSize]];
[paragraphStyle setLineSpacing:fontSize*0.3f];
[attributedString addAttribute:NSParagraphStyleAttributeName value:paragraphStyle range:NSMakeRange(0, [txt length])];
self.cardLabel.lineBreakMode = NSLineBreakByWordWrapping;
[self.cardLabel sizeToFit];
if (self.cardLabel.frame.size.width <= 220) {
[self.cardLabel setFrame:CGRectMake(40, 40, 220, self.cardLabel.frame.size.height)];
}
if (self.cardLabel.frame.size.height <= 210) {
[self.cardLabel setFrame:CGRectMake(40, 40, self.cardLabel.frame.size.width, 210)];
}
if (self.cardLabel.frame.size.width <= 220 && self.cardLabel.frame.size.height <= 210) {
[self.cardLabel setFrame:CGRectMake(40, 40, 220, 210)];
break;
}
};
-(void)setCardText:(NSString*)txt{
NSMUTABLeAttributeString*AttributeString=[[NSMUTABLeAttributeString alloc]initWithString:txt];
NSMutableParagraphStyle*paragraphStyle=[[NSMutableParagraphStyle alloc]init];
[段落样式setLineBreakMode:NSLineBreakByWordWrapping];
[段落样式setAlignment:NSTextAlignmentCenter];
[attributedString addAttribute:NSParagraphStyleAttributeName值:段落样式范围:NSMakeRange(0,[txt长度]);
self.cardLabel.attributedText=attributedString;
对于(CGFloat fontSize=40;fontSize>=5;fontSize--){
[self.cardLabel setFont:[UIFont fontWithName:@“GothamPro Light”大小:fontSize];
[段落样式设置行距:fontSize*0.3f];
[attributedString addAttribute:NSParagraphStyleAttributeName值:段落样式范围:NSMakeRange(0,[txt长度]);
self.cardLabel.lineBreakMode=NSLineBreakByWordWrapping;
[self.cardlelabel sizeToFit];
如果(self.cardLabel.frame.size.width您尝试过该属性吗?sizeToFit方法调用sizeThatFits:它返回“最佳”大小以适应当前的边界,然后调整标签的大小。因此,首先您约束标签,它必须适应给定的宽度。您可以看到-Wrapping的描述出现在单词边界处,除非单词本身不适合一行
出于您的目的,您应该允许标签的宽度比要求的宽度更宽。但这很困难,因为任务是找到最佳字体大小,而我们无法预测宽度。最好的方法是根据文本中最长的单词找到字体大小
因此,算法:
通过空格分隔来检测最长的单词
迭代地减小字体大小,并在单词大于所需宽度时计算最长单词的大小
将计算字体设置为全文,并调用sizeThatFits
请在下面找到示例代码(“Verdana”字体用于测试)
是的,但它在我的情况下不起作用,文字仍然被剪切。我尝试在我的中对循环使用adjustsFontSizeToFit
,对静音adjustsFontSizeToFitWidth
是常用的解决方案,但它只对单行标签有效。是的,除了使用组件部分,我做了相同的逻辑atedByCharactersInSet
,得到了没有附加标点符号的干净单词。但是你的方法更适合我。谢谢!
- (void) setText {
NSString * text = @"Incidental, indirect, secondary, side rival - Побочный, косвенный, второстепенный, боковой соперник";
CGFloat maxWidth = 300.;
[self setText:text toLabel:self.label maxWidth:maxWidth];
}
- (void) setText:(NSString *)text
toLabel:(UILabel*)label
maxWidth:(CGFloat)maxWidth
{
CGFloat fontSize = [self fontSizeOfWord:[self theLongestWord:text]
initialFontSize:40.
constrainedByWidth:maxWidth];
NSMutableAttributedString * attributedString = [self attributedStringForText:text];
[self setupAttributedStirng:attributedString withFontWithSize:fontSize];
label.attributedText = attributedString;
CGRect labelFrame = label.frame;
labelFrame.size = [label sizeThatFits:[attributedString sizeAdaptedForWidth:maxWidth]];
label.frame = labelFrame;
}
- (NSString*) theLongestWord:(NSString*)text {
NSArray * words = [text componentsSeparatedByString:@" "];
NSUInteger longestLength = 0;
NSUInteger index = NSNotFound;
for(int i = 0; i < words.count; i++) {
NSString * word = words[i];
CGFloat length = word.length;
if(length > longestLength) {
longestLength = length;
index = i;
}
}
return (index != NSNotFound ? words[index] : nil);
}
- (CGFloat)fontSizeOfWord:(NSString *)word
initialFontSize:(CGFloat)initialFontSize
constrainedByWidth:(CGFloat)maxWidth
{
NSMutableAttributedString * wordString = [self attributedStringForText:word];
CGFloat fontSize = initialFontSize;
for (; fontSize >= 5.; --fontSize) {
[self setupAttributedStirng:wordString
withFontWithSize:fontSize];
CGSize wordSize = [wordString sizeAdaptedForWidth:CGFLOAT_MAX];
if(wordSize.width <= maxWidth){
break;
}
}
return fontSize;
}
- (NSMutableAttributedString*) attributedStringForText:(NSString*)text {
return (text&&text.length ? [[NSMutableAttributedString alloc] initWithString:text]:nil);
}
- (void)setupAttributedStirng:(NSMutableAttributedString *)attributedString
withFontWithSize:(CGFloat)fontSize
{
NSMutableParagraphStyle *paragraphStyle = [NSMutableParagraphStyle new];
[paragraphStyle setLineBreakMode:NSLineBreakByWordWrapping];
[paragraphStyle setAlignment:NSTextAlignmentCenter];
UIFont * font = [UIFont fontWithName:@"Verdana" size:fontSize];
[paragraphStyle setLineSpacing:fontSize*0.3f];
NSDictionary * attributes = @{NSParagraphStyleAttributeName: paragraphStyle,
NSFontAttributeName: font};
[attributedString addAttributes:attributes
range:NSMakeRange(0, [attributedString length])];
}
@implementation NSAttributedString (AdaptedSize)
- (CGSize) sizeAdaptedForWidth:(CGFloat)width
{
CTFramesetterRef framesetter = CTFramesetterCreateWithAttributedString((__bridge CFAttributedStringRef)self);
CGSize targetSize = CGSizeMake(width, CGFLOAT_MAX);
CGSize fitSize = CTFramesetterSuggestFrameSizeWithConstraints(framesetter,
CFRangeMake(0, [self length]),
NULL, targetSize, NULL);
CFRelease(framesetter);
return fitSize;
}
@end