I\'ve got this basic like script that I need to convert to objective c, it turns big units of money into shortened versions (ie: 1.2m, etc), I\'ve got most of the conversion
Just to improve the solution, a good idea is maybe to subclass the NSNumberFormatter class and override the - (NSString *)stringForObjectValue:(id)anObject method.
Using the code from zardon, I added a statement for the values < 1000 which doesn't format the number.
Here is the code of the method :
/*
Override the stringForObjectValue method from NSNumberFormatter
100 -> 100
1000 -> 1k
1 000 000 -> 1m
1 000 000 000 -> 1b
1 000 000 000 -> 1t
*/
- (NSString *)stringForObjectValue:(id)anObject {
// If we don't get a NSNumber, we can't create the string
if (![anObject isKindOfClass:[NSNumber class]]) {
return nil;
}
NSNumberFormatter *nformat = [[NSNumberFormatter alloc] init];
// Decimal value from the NSObject
double doubleValue = [anObject doubleValue];
NSString *stringValue = nil;
// Abbrevations used
NSArray *abbrevations = [NSArray arrayWithObjects:@"k", @"m", @"b", @"t", nil] ;
// If the value is less than 1000, we display directly the value
if(doubleValue < 1000.0) {
stringValue = [NSString stringWithFormat: @"%@", [nformat stringFromNumber: [NSNumber numberWithDouble: doubleValue]] ];
}
else { // Otherwise we format it as expected
for (NSString *s in abbrevations) {
doubleValue /= 1000.0 ;
if ( doubleValue < 1000.0 ) {
if ( (long long)doubleValue % (long long) 100 == 0 ) {
[nformat setMaximumFractionDigits:0];
} else {
[nformat setMaximumFractionDigits:2];
}
stringValue = [NSString stringWithFormat: @"%@", [nformat stringFromNumber: [NSNumber numberWithDouble: doubleValue]] ];
NSUInteger stringLen = [stringValue length];
if ( [stringValue hasSuffix:@".00"] )
{
// Remove suffix
stringValue = [stringValue substringWithRange: NSMakeRange(0, stringLen-3)];
} else if ( [stringValue hasSuffix:@".0"] ) {
// Remove suffix
stringValue = [stringValue substringWithRange: NSMakeRange(0, stringLen-2)];
} else if ( [stringValue hasSuffix:@"0"] ) {
// Remove suffix
stringValue = [stringValue substringWithRange: NSMakeRange(0, stringLen-1)];
}
// Add the letter suffix at the end of it
stringValue = [stringValue stringByAppendingString: s];
break;
}
}
}
[nformat release];
return stringValue;
}
In the interface we simply add the inheritage statement :
@interface MoneyNumberFormatter : NSNumberFormatter
Hope this helps..
.... Okay, with thanks to the author of the Cocoa Tidbits blog, I believe I have a solution which is much more elegant, faster and doesn't require so much coding; it still needs testing, and it also probably requires a little more editing, but it seems to be much better than my original.
I modified the script a little to make it not show any trailing zeros where relevant;
NSNumberFormatter *nformat = [[NSNumberFormatter alloc] init];
[nformat setFormatterBehavior:NSNumberFormatterBehavior10_4];
[nformat setCurrencySymbol:@"$"];
[nformat setNumberStyle:NSNumberFormatterCurrencyStyle];
double doubleValue = 10200;
NSString *stringValue = nil;
NSArray *abbrevations = [NSArray arrayWithObjects:@"k", @"m", @"b", @"t", nil] ;
for (NSString *s in abbrevations)
{
doubleValue /= 1000.0 ;
if ( doubleValue < 1000.0 )
{
if ( (long long)doubleValue % (long long) 100 == 0 ) {
[nformat setMaximumFractionDigits:0];
} else {
[nformat setMaximumFractionDigits:2];
}
stringValue = [NSString stringWithFormat: @"%@", [nformat stringFromNumber: [NSNumber numberWithDouble: doubleValue]] ];
NSUInteger stringLen = [stringValue length];
if ( [stringValue hasSuffix:@".00"] )
{
// Remove suffix
stringValue = [stringValue substringWithRange: NSMakeRange(0, stringLen-3)];
} else if ( [stringValue hasSuffix:@".0"] ) {
// Remove suffix
stringValue = [stringValue substringWithRange: NSMakeRange(0, stringLen-2)];
} else if ( [stringValue hasSuffix:@"0"] ) {
// Remove suffix
stringValue = [stringValue substringWithRange: NSMakeRange(0, stringLen-1)];
}
// Add the letter suffix at the end of it
stringValue = [stringValue stringByAppendingString: s];
//stringValue = [NSString stringWithFormat: @"%@%@", [nformat stringFromNumber: [NSNumber numberWithDouble: doubleValue]] , s] ;
break ;
}
}
NSLog(@"Cash = %@", stringValue);