我使用NSLengthFormatter类格式化用户与某个目的地之间的距离。
CLLocation *userLocation; //<- Coordinates fetched from CLLocationManager
CLLocation *targetLocation; //<- Some location retrieved from server data
CLLocationDistance distance = [userLocation distanceFromLocation:targetLocation];
NSLengthFormatter *lengthFormatter = [NSLengthFormatter new];
NSString *formattedLength = [lengthFormatter stringFromMeters:distance];
现在,如果长度小于1000米,则格式化的距离始终以码或米显示(取决于区域设置)。
EG。如果距离= 450.0,格式化的字符串将是492.7码或450米。
如何调整NSLengthFormatter以仅以英里/公里为单位返回距离字符串?
答案 0 :(得分:8)
这就是我最终使用的内容:
-(NSString *)formattedDistanceForMeters:(CLLocationDistance)distance
{
NSLengthFormatter *lengthFormatter = [NSLengthFormatter new];
[lengthFormatter.numberFormatter setMaximumFractionDigits:1];
if ([[[NSLocale currentLocale] objectForKey:NSLocaleUsesMetricSystem] boolValue])
{
return [lengthFormatter stringFromValue:distance / 1000 unit:NSLengthFormatterUnitKilometer];
}
else
{
return [lengthFormatter stringFromValue:distance / 1609.34 unit:NSLengthFormatterUnitMile];
}
}
答案 1 :(得分:3)
似乎没有办法选择退出此行为。说实话,从UX的角度来看,您的要求并不常见。
请注意,meter
是基本单位,而不是kilometer
(千米)。通常,显示10 meters
比显示0.01 kilometers
更受欢迎。它对用户来说更友好。
考虑到基本单元依赖于当前区域设置,实际上很难设计一个强制执行特定单元的API。
您可以使用以下方式强制执行特定单位:
- (NSString *)unitStringFromValue:(double)value unit:(NSLengthFormatterUnit)unit;
但你必须处理语言环境和缩放&amp;单位转换(参见Objective c string formatter for distances)
答案 2 :(得分:0)
对于不使用公制的人们来说,这实际上是一个非常普遍的要求(是的,我知道...)。
在公制中,从公里到米等都是有意义的。如果对英制遵循相同的逻辑,则将从英里到码到英尺。
通常,您不想使用“码”作为道路距离,并且您不想显示5,000 ft但显示0.9英里(实际上Google Maps以英尺为单位显示最大0.1英里或528英尺,然后以英里为单位)
let distanceAsDouble = 415.0
let lengthFormatter = LengthFormatter()
if Locale.current.usesMetricSystem {
return distanceFormatter.string(fromMeters: distanceAsDouble)
} else {
let metersInOneMile = Measurement<UnitLength>(value: 1.0, unit: .miles).converted(to: .meters).value
if distanceAsDouble < metersInOneMile / 10 { // Display feets from 0 to 0.1 mi, then miles
let distanceInFeets = Measurement<UnitLength>(value: distanceAsDouble, unit: .meters).converted(to: .feet).value
return distanceFormatter.string(fromValue: distanceInFeets, unit: .foot)
} else {
return distanceFormatter.string(fromValue: distanceAsDouble / metersInOneMile, unit: .mile)
}
}