Get currency symbols from currency code with swift

前端 未结 11 589
星月不相逢
星月不相逢 2020-12-24 12:21

How can I get the currency symbols for the corresponding currency code with Swift (macOS).

Example:

  • EUR = €1.00
  • USD = $1.00<
相关标签:
11条回答
  • 2020-12-24 12:51

    You can use static 'availableIdentifiers' collection, containing all posible identifiers as follows:

    extension Locale {
        static func locale(from currencyIdentifier: String) -> Locale? {
            let allLocales = Locale.availableIdentifiers.map({ Locale.init(identifier: $0) })
            return allLocales.filter({ $0.currencyCode == currencyIdentifier }).first
        }
    }
    
    0 讨论(0)
  • 2020-12-24 12:52
    SWIFT4 
    //converting USD to $a and GBP to £ 
    viewDidLoad() 
    { 
     print(getSymbolForCurrencyCode(code: "USD")!) // prints $ 
     print(getSymbolForCurrencyCode(code: "GBP")!) //prints £ 
    }
    
    func getSymbolForCurrencyCode(code: String) -> String? 
    { 
      let locale = NSLocale(localeIdentifier: code)
      return locale.displayName(forKey: NSLocale.Key.currencySymbol, value: code) 
    }
    
    0 讨论(0)
  • 2020-12-24 12:52

    An imperfect solution I found to get $ instead of US$ or CA$ was to attempt to match the user's current locale to the currency code first. This will work for situations where you're building a mobile app and an API is sending you currency code based on the settings in that user's account. For us the business case is that 99% of users have the same currency code set in their account on the backend (USD, CAD, EUR, etc.), where we're getting the information from, as they do on their mobile app where we're displaying currency the way a user would expect to see it (i.e. $50.56 instead of US$ 50.56).

    Objective-C

    - (NSLocale *)localeFromCurrencyCode:(NSString *)currencyCode {
        NSLocale *locale = [NSLocale currentLocale];
        if (![locale.currencyCode isEqualToString:currencyCode]) {
            NSDictionary *localeInfo = @{NSLocaleCurrencyCode:currencyCode};
            locale = [[NSLocale alloc] initWithLocaleIdentifier:[NSLocale localeIdentifierFromComponents:localeInfo]];
        }
        return locale;
    }
    

    Swift

    func locale(from currencyCode: String) -> Locale {
        var locale = Locale.current
        if (locale.currencyCode != currencyCode) {
            let identifier = NSLocale.localeIdentifier(fromComponents: [NSLocale.Key.currencyCode.rawValue: currencyCode])
            locale = NSLocale(localeIdentifier: identifier) as Locale
        }
        return locale;
    }
    
    0 讨论(0)
  • 2020-12-24 12:53

    Swift 4 Version of Pancho's answer, As the String.characters is deprecated now.

    We can simply apply dropLast() on String.

    func getCurrencySymbol(from currencyCode: String) -> String? {
    
        let locale = NSLocale(localeIdentifier: currencyCode)
        if locale.displayName(forKey: .currencySymbol, value: currencyCode) == currencyCode {
            let newlocale = NSLocale(localeIdentifier: currencyCode.dropLast() + "_en")
            return newlocale.displayName(forKey: .currencySymbol, value: currencyCode)
        }
        return locale.displayName(forKey: .currencySymbol, value: currencyCode)
    }
    
    0 讨论(0)
  • 2020-12-24 12:55
    let countryCode = (Locale.current as NSLocale).object(forKey: .currencySymbol) as? String ?? "$"
    

    Above will give current currency Symbol, For UK it gives me = £ Apple Doc

    0 讨论(0)
  • 2020-12-24 13:06

    I combined and improved all the suggestion here to have a drop-in(copy/paste) solution for the future readers(you).

    It has its own local cache, case insensitive, and have an extension method to provide chaining for String. Swift 4/5 ready.

    How to use:

    "USD".currencySymbol //returns "$"
    //OR
    Currency.shared.findSymbol(currencyCode: "TRY") //returns "₺"
    

    Tests:

        XCTAssertEqual("$", "USD".currencySymbol)
        XCTAssertEqual("₺", "TRY".currencySymbol)
        XCTAssertEqual("€", "EUR".currencySymbol)
        XCTAssertEqual("", "ASDF".currencySymbol)
    

    Code:

    class Currency {
        static let shared: Currency = Currency()
    
        private var cache: [String:String] = [:]
    
        func findSymbol(currencyCode:String) -> String {
            if let hit = cache[currencyCode] { return hit }
            guard currencyCode.count < 4 else { return "" }
    
            let symbol = findSymbolBy(currencyCode)
            cache[currencyCode] = symbol
    
            return symbol
        }
    
        private func findSymbolBy(_ currencyCode: String) -> String {
            var candidates: [String] = []
            let locales = NSLocale.availableLocaleIdentifiers
    
            for localeId in locales {
                guard let symbol = findSymbolBy(localeId, currencyCode) else { continue }
                if symbol.count == 1 { return symbol }
                candidates.append(symbol)
            }
    
            return candidates.sorted(by: { $0.count < $1.count }).first ?? ""
        }
    
        private func findSymbolBy(_ localeId: String, _ currencyCode: String) -> String? {
            let locale = Locale(identifier: localeId)
            return currencyCode.caseInsensitiveCompare(locale.currencyCode ?? "") == .orderedSame
                ? locale.currencySymbol : nil
        }
    }
    
    extension String {
        var currencySymbol: String { return Currency.shared.findSymbol(currencyCode: self) }
    }
    
    0 讨论(0)
提交回复
热议问题