2011-01-25 24 views

回答

0

爲什麼不編碼來計算字符串的長度,如果它的字符串超過了視圖,就使它的子字符串。或做任何你想要 它是原始而有效的方法

+0

這會不會僅可靠地固定寬度字體工作? – Dolbz 2011-01-25 15:11:49

+0

我不是說用這個做任何標準api。字體規格將根據我的要求進行修正。 – Javanator 2011-01-25 15:53:54

0

您還可以設置

[lbl setAdjustsFontSizeToFitWidth:YES]; 

有了這個就沒有必要截斷的文字,你可以在你的label顯示完整的文本。

1

-[UILabel setLineBreakMode:]UILineBreakModeCharacterWrap-[UILabel lineBreakMode]的默認值是UILineBreakModeTailTruncation,這會導致末尾的省略號。

0

由於Javanator說你不得不做自己的截斷。您可以使用UIKit添加到NSString類中的 sizeWithFont:forWidth:lineBreakMode:消息來獲取具有特定字體的字符串的寬度。這將處理所有類型的字體。

Link

9

我寫了一個自定義的截斷類,您可以跳進你的代碼在以往任何時候。請使用下面的方法。如果截斷髮生,它將返回true,如果你只想使用標籤的默認幀寬,MaxWidth可以保留爲0。將maxWidth設置爲小於幀寬度的值,以在其幀範圍內縮短它。

夫特2(帶有用於將一些迅速3條評論)

用法:

Truncater.replaceElipsis(forLabel: label, withString: "???") 
let didTruncate = Truncater.replaceElipsis(forLabel: label, withString: "1234", andMaximumWidth: 50) //maxWidth is not number of chars, but label width in CGFloat 

類:

import UIKit 

class Truncater { 

    class func replaceElipsis(forLabel label:UILabel, withString replacement:String) -> Bool { 
     return replaceElipsis(forLabel: label, withString: replacement, andMaximumWidth:0) 
    } 

    class func replaceElipsis(forLabel label:UILabel, withString replacement:String, andMaximumWidth width:CGFloat) -> Bool { 

     if(label.text == nil){ 
      return false 
     } 

     let origSize = label.frame; 
     var useWidth = width 

     if(width <= 0){ 
      useWidth = origSize.width //use label width by default if width <= 0 
     } 

     label.sizeToFit() 
     let labelSize = label.text!.sizeWithAttributes([NSFontAttributeName: label.font]) //.size(attributes: [NSFontAttributeName: label.font]) for swift 3 

     if(labelSize.width > useWidth){ 

      let original = label.text!; 
      let truncateWidth = useWidth; 
      let font = label.font; 
      let subLength = label.text!.characters.count 

      var temp = label.text!.substringToIndex(label.text!.endIndex.advancedBy(-1)) //label.text!.substring(to: label.text!.index(label.text!.endIndex, offsetBy: -1)) for swift 3 
      temp = temp.substringToIndex(temp.startIndex.advancedBy(getTruncatedStringPoint(subLength, original:original, truncatedWidth:truncateWidth, font:font, length:subLength))) 
      temp = String.localizedStringWithFormat("%@%@", temp, replacement) 

      var count = 0 

      while temp.sizeWithAttributes([NSFontAttributeName: label.font]).width > useWidth { 

       count+=1 

       temp = label.text!.substringToIndex(label.text!.endIndex.advancedBy(-(1+count))) 
       temp = temp.stringByTrimmingCharactersInSet(NSCharacterSet.whitespaceCharacterSet()) //remove this if you want to keep whitespace on the end 
       temp = String.localizedStringWithFormat("%@%@", temp, replacement) 
      } 

      label.text = temp; 
      label.frame = origSize; 
      return true; 
     } 
     else { 

      label.frame = origSize; 
      return false 
     } 
    } 

    class func getTruncatedStringPoint(splitPoint:Int, original:String, truncatedWidth:CGFloat, font:UIFont, length:Int) -> Int { 

     let splitLeft = original.substringToIndex(original.startIndex.advancedBy(splitPoint)) 

     let subLength = length/2 

     if(subLength <= 0){ 
      return splitPoint 
     } 

     let width = splitLeft.sizeWithAttributes([NSFontAttributeName: font]).width 

     if(width > truncatedWidth) { 
      return getTruncatedStringPoint(splitPoint - subLength, original: original, truncatedWidth: truncatedWidth, font: font, length: subLength) 
     } 
     else if (width < truncatedWidth) { 
      return getTruncatedStringPoint(splitPoint + subLength, original: original, truncatedWidth: truncatedWidth, font: font, length: subLength) 
     } 
     else { 
      return splitPoint 
     } 
    } 
} 

目標C

+ (bool) replaceElipsesForLabel:(UILabel*) label With:(NSString*) replacement MaxWidth:(float) width 

類:

//=============================================Header===================================================== 
#import <Foundation/Foundation.h> 
#import <UIKit/UIKit.h> 

@interface CustomTruncater : NSObject 

+ (bool) replaceElipsesForLabel:(UILabel*) label With:(NSString*) replacement MaxWidth:(float) width; 

@end 

//======================================================================================================== 

#import "CustomTruncater.h" 

@implementation CustomTruncater 

static NSString *original; 
static float truncateWidth; 
static UIFont *font; 
static int subLength; 

+ (bool) replaceElipsesForLabel:(UILabel*) label With:(NSString*) replacement MaxWidth:(float) width { 

CGRect origSize = label.frame; 

float useWidth = width; 

if(width <= 0) 
    useWidth = origSize.size.width; //use label width by default if width <= 0 

[label sizeToFit]; 
CGSize labelSize = [label.text sizeWithFont:label.font]; 

if(labelSize.width > useWidth) { 

    original = label.text; 
    truncateWidth = useWidth; 
    font = label.font; 
    subLength = label.text.length; 

    NSString *temp = [label.text substringToIndex:label.text.length-1]; 
    temp = [temp substringToIndex:[self getTruncatedStringPoint:subLength]]; 
    temp = [NSString stringWithFormat:@"%@%@", temp, replacement]; 

    int count = 0; 

    while([temp sizeWithFont:label.font].width > useWidth){ 

     count++; 

     temp = [label.text substringToIndex:(label.text.length-(1+count))]; 
     temp = [temp stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceCharacterSet]]; //remove this if you want to keep whitespace on the end 
     temp = [NSString stringWithFormat:@"%@%@", temp, replacement]; 
    } 

    label.text = temp; 
    label.frame = origSize; 
    return true; 
} 
else { 
    label.frame = origSize; 
    return false; 
} 
} 

+ (int) getTruncatedStringPoint:(int) splitPoint { 

NSString *splitLeft = [original substringToIndex:splitPoint]; 
subLength /= 2; 

if(subLength <= 0) 
    return splitPoint; 

if([splitLeft sizeWithFont:font].width > truncateWidth){ 
    return [self getTruncatedStringPoint:(splitPoint - subLength)]; 
} 
else if ([splitLeft sizeWithFont:font].width < truncateWidth) { 
    return [self getTruncatedStringPoint:(splitPoint + subLength)]; 
} 
else { 
    return splitPoint; 
} 
} 

@end