iOS 7で非推奨の-sizeWithFont:constrainedToSize:lineBreakMode:の代替ですか?


146

iOS 7では、メソッド:

- (CGSize)sizeWithFont:(UIFont *)font
     constrainedToSize:(CGSize)size
         lineBreakMode:(NSLineBreakMode)lineBreakMode 

そして方法:

- (CGSize)sizeWithFont:(UIFont *)font

廃止予定です。どうすれば交換できますか

CGSize size = [string sizeWithFont:font
                 constrainedToSize:constrainSize
                     lineBreakMode:NSLineBreakByWordWrapping];

そして:

CGSize size = [string sizeWithFont:font];

2
代替方法は-sizeWithAttributes:です。
holex

よろしくお願いしますが、NSDIctionaryのようなラベルのフォントを使用するにはどうすればよいですか?私のコードが次のような場合:sizeWithFont:customlabel.font; void ask "sizeWithAttributes:<#(NSDictionary *)#>"
user_Dennis_Mostajo

1
これは、属性を定義する方法の公式ドキュメントです:developer.apple.com/library/ios/documentation/UIKit/Reference/…
holex

回答:


219

あなたはこれを試すことができます:

CGRect textRect = [text boundingRectWithSize:size
                                 options:NSStringDrawingUsesLineFragmentOrigin
                              attributes:@{NSFontAttributeName:FONT}
                                 context:nil];

CGSize size = textRect.size;

「[UIFont font ....]」の「FONT」を変更するだけです


13
そして、どこでNSLineBreakByWordWrappingについて言及しますか?どこへ行ったの?
user4951 2013年

31
NSLineBreakByWordWrapping内に移動しますNSParagraphStyle。したがって、たとえばNSMutableParagraphStyle *paragraphStyle = [[NSMutableParagraphStyle alloc] init]; paragraphStyle.lineBreakMode = NSLineBreakByWordWrapping;、属性に追加する必要がありNSParagraphStyleAttributeName: paragraphStyle.copyます...
Florian Friedrich

1
@ffried私の場合、NSLineBreakByWordWrapping以外の改行を含む段落スタイルを追加すると、サイズが1行だけで計算されるようになりました…
manicaesar 2014

9
boundingRectWithSize:options:attributes:context:小数の値を返すことを忘れないでください。実際の高さ/幅を取得するにはceil(textRect.size.height)ceil(textRect.size.width)それぞれを実行する必要があります。
フロリアンフリードリヒ

20
BOLIVIASizeとは一体何ですか?
JRam13 2014年

36

4.3以降のすべてのiOSでsizeWithAttributesを使用することはできないため、7.0以前のiOS用の条件付きコードを記述する必要があります。

1)ソリューション1:

if (SYSTEM_VERSION_GREATER_THAN_OR_EQUAL_TO(@"7.0")) {
   CGSize size = CGSizeMake(230,9999);
   CGRect textRect = [specialityObj.name  
       boundingRectWithSize:size
                    options:NSStringDrawingUsesLineFragmentOrigin
                 attributes:@{NSFontAttributeName:[UIFont fontWithName:[AppHandlers zHandler].fontName size:14]}
                    context:nil];
   total_height = total_height + textRect.size.height;   
}
else {
   CGSize maximumLabelSize = CGSizeMake(230,9999); 
   expectedLabelSize = [specialityObj.name sizeWithFont:[UIFont fontWithName:[AppHandlers zHandler].fontName size:14] constrainedToSize:maximumLabelSize lineBreakMode:UILineBreakModeWordWrap]; //iOS 6 and previous. 
   total_height = total_height + expectedLabelSize.height;
}

2)ソリューション2

UILabel *gettingSizeLabel = [[UILabel alloc] init];
gettingSizeLabel.font = [UIFont fontWithName:[AppHandlers zHandler].fontName size:16]; // Your Font-style whatever you want to use.
gettingSizeLabel.text = @"YOUR TEXT HERE";
gettingSizeLabel.numberOfLines = 0;
CGSize maximumLabelSize = CGSizeMake(310, 9999); // this width will be as per your requirement

CGSize expectedSize = [gettingSizeLabel sizeThatFits:maximumLabelSize];

最初の解決策は、適切な高さの値を返せないことがあります。別のソリューションを使用してください。完璧に動作します。

2番目のオプションは非常に適切で、条件付きコードなしですべてのiOSでスムーズに機能します。


1
なぜ230、999なのか?番号はどこにありますか?
user4951 2013年

1
230は任意の数にすることができます。ラベルに必要な幅を表します。9999はINFINITYまたはMAXFLOATで置き換えたいと思います。
フロリアンフリードリヒ

第二の解決策は魅力のように働いています。ありがとうNirav。
ジム

1
「[AppHandlers zHandler]」はエラーを返します。「宣言されていない識別子」。それを解決するには?
ディンプル2014年

9

ここに簡単な解決策があります:

要件:

CGSize maximumSize = CGSizeMake(widthHere, MAXFLOAT);
UIFont *font = [UIFont systemFontOfSize:sizeHere];

今すぐとしてconstrainedToSizeusage:lineBreakMode:の使用は非推奨にされてのiOS 7.0

CGSize expectedSize = [stringHere sizeWithFont:font constrainedToSize:maximumSize lineBreakMode:NSLineBreakByWordWrapping];

今での使用に大きいのバージョンのiOS 7.0は、次のようになります。

// Let's make an NSAttributedString first
NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc] initWithString:stringHere];
//Add LineBreakMode
NSMutableParagraphStyle *paragraphStyle = [NSMutableParagraphStyle new];
[paragraphStyle setLineBreakMode:NSLineBreakByWordWrapping];
[attributedString setAttributes:@{NSParagraphStyleAttributeName:paragraphStyle} range:NSMakeRange(0, attributedString.length)];
// Add Font
[attributedString setAttributes:@{NSFontAttributeName:font} range:NSMakeRange(0, attributedString.length)];

//Now let's make the Bounding Rect
CGSize expectedSize = [attributedString boundingRectWithSize:maximumSize options:NSStringDrawingUsesLineFragmentOrigin context:nil].size;

7

以下は、これら2つの廃止されたメソッドを置き換える2つの単純なメソッドです。

そしてここに関連する参照があります:

NSLineBreakByWordWrappingを使用している場合は、デフォルトであるNSParagraphStyleを指定する必要はありません。https://developer.apple.com/library/mac/documentation/Cocoa/Reference/ApplicationKit/Classes/NSParagraphStyle_Class/index 。 html#// apple_ref / occ / clm / NSParagraphStyle / defaultParagraphStyle

非推奨のメソッドの結果と一致するように、サイズの上限を取得する必要があります。 https://developer.apple.com/library/ios/documentation/UIKit/Reference/NSString_UIKit_Additions/#//apple_ref/occ/instm/NSString/boundingRectWithSize:options:attributes:context

+ (CGSize)text:(NSString*)text sizeWithFont:(UIFont*)font {    
    CGSize size = [text sizeWithAttributes:@{NSFontAttributeName: font}];
    return CGSizeMake(ceilf(size.width), ceilf(size.height));
}

+ (CGSize)text:(NSString*)text sizeWithFont:(UIFont*)font constrainedToSize:(CGSize)size{
    CGRect textRect = [text boundingRectWithSize:size
                                     options:NSStringDrawingUsesLineFragmentOrigin
                                  attributes:@{NSFontAttributeName: font}
                                     context:nil];
    return CGSizeMake(ceilf(textRect.size.width), ceilf(textRect.size.height));
}

6

ほとんどの場合、メソッドsizeWithFont:constrainedToSize:lineBreakMode:を使用して、UILabelがそのテキストに対応するための最小サイズを推定しました(特に、ラベルをUITableViewCell内に配置する必要がある場合)...

...これがまさにあなたの状況であるなら、あなたはメソッドを使うことができます:

CGSize size = [myLabel textRectForBounds:myLabel.frame limitedToNumberOfLines:mylabel.numberOfLines].size;

これが役立つことを願っています。


5
Appleのドキュメントには、このメソッドを直接呼び出さないように記載されています。
Barlow Tucker

少なくともiOS 7 SDKのドキュメントには記載されていません。
Rivera

3
UIFont *font = [UIFont boldSystemFontOfSize:16];
CGRect new = [string boundingRectWithSize:CGSizeMake(200, 300) options:NSStringDrawingUsesFontLeading attributes:@{NSFontAttributeName: font} context:nil];
CGSize stringSize= new.size;

3
StackOverFlowへようこそ。同じ回答を再度投稿しないでください。回答に何かを追加する必要がある場合は、コメントを作成するか、回答を編集してください。
Ramaraj T 2014

わかりました。次回はその点を考慮します。アドバイスありがとうございます。
user3575114 14

2

[承認された回答はカテゴリでうまく機能します。非推奨のメソッド名を上書きしています。これは良い考えですか?Xcode 6.xでは問題なく動作するようです]

これは、デプロイメントターゲットが7.0以上の場合に機能します。カテゴリーはNSString (Util)

NSString + Util.h

- (CGSize)sizeWithFont:(UIFont *) font;
- (CGSize)sizeWithFont:(UIFont *)font constrainedToSize:(CGSize)size;

NSString + Util.m

- (CGSize)sizeWithFont:(UIFont *) font {
    NSDictionary *fontAsAttributes = @{NSFontAttributeName:font};
    return [self sizeWithAttributes:fontAsAttributes];
}

- (CGSize)sizeWithFont:(UIFont *)font constrainedToSize:(CGSize)size {
    NSDictionary *fontAsAttributes = @{NSFontAttributeName:font};
    CGRect retVal = [self boundingRectWithSize:size
                                     options:NSStringDrawingUsesLineFragmentOrigin
                                  attributes:fontAsAttributes context:nil];
    return retVal.size;
}

0
UIFont *font = [UIFont fontWithName:@"Courier" size:16.0f];

NSMutableParagraphStyle *paragraphStyle = [[NSParagraphStyle defaultParagraphStyle] mutableCopy];
paragraphStyle.lineBreakMode = NSLineBreakByTruncatingTail;
paragraphStyle.alignment = NSTextAlignmentRight;

NSDictionary *attributes = @{ NSFontAttributeName: font,
                    NSParagraphStyleAttributeName: paragraphStyle };

CGRect textRect = [text boundingRectWithSize:size
                                 options:NSStringDrawingUsesLineFragmentOrigin
                              attributes:attributes
                                 context:nil];

CGSize size = textRect.size;

2つの答えから1 + 2

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.