SwiftUI多变量字符串本地化咨询:多插值的多语言适配方案
多变量本地化的可行方案
1. 使用带位置标识的格式占位符
这是iOS原生支持的标准方案,通过给占位符添加位置索引(如%1$@、%2$d),能明确指定每个占位符对应代码里的变量,既解决不同语言中变量位置调换的问题,也能区分变量类型(%@对应字符串、%d对应整数、%f对应浮点数等)。
示例:
在Localizable.strings文件中:
// 英文 "userInfo" = "My Name is %1$@ and I am %2$d years old"; // 中文(调换变量位置) "userInfo" = "我叫%1$@,今年%2$d岁"; // 日语(调整占位符顺序) "userInfo" = "%2$d歳の%1$@です";
代码中调用:
let name = "Alice" let age = 25 let localizedText = String(format: NSLocalizedString("userInfo", comment: "User info with name and age"), name, age)
这里%1$@固定对应第一个传入的name,%2$d对应第二个age,无论翻译文本里占位符位置怎么变,变量对应关系都不会出错。
2. 自定义命名占位符(更易读)
如果觉得数字占位符不够直观,可使用{name}、{age}这类命名式占位符,自己写简单的替换逻辑。这种方式对译者更友好,能直接看懂每个占位符代表的内容。
示例:
在Localizable.strings文件中:
// 英文 "userInfo" = "My Name is {name} and I am {age} years old"; // 中文 "userInfo" = "我叫{name},今年{age}岁";
代码实现替换逻辑:
extension String { func localized(with replacements: [String: Any]) -> String { var result = NSLocalizedString(self, comment: "") for (key, value) in replacements { result = result.replacingOccurrences(of: "{\(key)}", with: "\(value)") } return result } } // 使用方式 let name = "Bob" let age = 30 let localizedText = "userInfo".localized(with: ["name": name, "age": age])
3. 富文本场景的处理
如果本地化文本需要不同字体、颜色等格式,可结合NSMutableAttributedString和占位符实现,既能替换变量,也能保留格式设置。
示例:
// Localizable.strings "richUserInfo" = "My Name is {name} and I am {age} years old"; // 代码中构建富文本 let baseString = NSLocalizedString("richUserInfo", comment: "") let attributedString = NSMutableAttributedString(string: baseString) // 替换name并设置蓝色字体 let nameRange = attributedString.mutableString.range(of: "{name}") attributedString.replaceCharacters(in: nameRange, with: "Charlie") attributedString.addAttribute(.foregroundColor, value: UIColor.blue, range: NSRange(location: nameRange.location, length: "Charlie".count)) // 替换age并设置红色字体 let ageRange = attributedString.mutableString.range(of: "{age}") attributedString.replaceCharacters(in: ageRange, with: "28") attributedString.addAttribute(.foregroundColor, value: UIColor.red, range: NSRange(location: ageRange.location, length: "28".count))
内容的提问来源于stack exchange,提问作者IOSCodingMax
相关产品推荐
相关产品推荐

