我想将标签设置为字符串:“خخخ 刚刚购买:伪装工具包。” 但是当我运行测试时,标签显示“。刚刚购买:伪装工具包خخخ”?
如果文本不是以阿拉伯语开头,它将显示为我设置的内容。有什么问题?
有人知道如何处理这个问题吗?
首先,阅读 Cal Henderson 出色的“理解 Unicode 中的双向 (BIDI) 文本”。.
信不信UILabel
由你,按照你要求的方式进行布局。您提供了一个从右到左的字符串(以阿拉伯语开头)。它开始从右到左显示。然后,您嵌入了一个从左到右的英文字符串,它从左到右排列。然后它会看到句点,并将其从右到左排列,因为这是一个阿拉伯字符串,恰好包含一些英语(正如最好的说法UILabel
)。
你想要的是一个嵌入了阿拉伯语的从左到右的字符串。这意味着您必须以从左到右的字符开始字符串。两个选项:在开头添加一些英文,或者使用零宽度的从左到右标记(U+200E,LRM)将字符串的开头锚定为 LTR 模式。
目标-C:
self.label.text = @"\u200eكتب just bought: Disguise Kit.";
迅速:
self.label.text = "\u{200E}كتب just bought: Disguise Kit."
关于 U+200E 的好消息是,您可以在显示之前安全地将其添加到每个 LTR 字符串中。您甚至可以安全地将其放在 LTR 语言的本地化字符串的开头。如果它是多余的,它不会伤害任何东西。
还有一些需要注意的事情:永远不要用ككك测试这些东西,总是用كتب(就像每个好学生:D)或更好的东西,比如الو。否则,您无法判断阿拉伯语何时向后布局。我喜欢الو,因为它向后看起来完全不同。
另外,在测试时,请注意 Xcode 不知道如何布局阿拉伯语。因此,如果您在代码中编写任何静态字符串,它们将在编辑器中向后显示,但它们会在 UI 中正确显示。让我发狂。
请务必查看 guru_meditator 对 iOS 10+/macOS 10.12 中添加的有用相关功能的回答。
由于 iOS 10(和 macOS 10.12)String localizedStringWithFormat
在占位符周围插入 Unicode 隔离。这是使用混合语言方向格式化字符串的高级方法,无需手动插入方向标记。
String.localizedStringWithFormat("%@ just bought: Disguise Kit.", "خخخ")
// "خخخ just bought: Disguise Kit."
相比于:
String(format: "%@ just bought: Disguise Kit.", "خخخ")
// ".just bought: Disguise Kit خخخ"
要查看localizedStringWithFormat 正在做什么:
let scalars = String.localizedStringWithFormat("%@ just bought: Disguise Kit.", "خخخ")
.unicodeScalars.map { "U+\(String(format: "%04X", $0.value))" }
print(scalars)
// ["U+2068", "U+062E", "U+062E", "U+062E", "U+2069", "U+0020", ...
其中 U+2068 是 FIRST STRONG ISOLATE,U+2069 是 POP DIRECTIONAL ISOLATE。您可以阅读更多关于隔离的信息:https ://www.unicode.org/reports/tr9/tr9-41.html#Explicit_Directional_Isolates
实际上, \u{200E} (或任何)符号可以插入到字符串文字中。