Furigana(也称为rubi)是日语阅读辅助工具,由汉字(表意字符)旁边印刷的小假名或音节字符组成
我在互联网上找到了如何通过以下代码在UILable中显示假名:
<table datatable [dtOptions]="dtOptions" [dtTrigger]="dtTrigger" class="display nowrap" cellspacing="0" width="100%" >
我是Swift的新手,所以我只是复制并粘贴到我的x-code项目,但它无法正常工作(错误:无法将类型&#39;未管理&#39;的值转换为预期的参数类型&# 39; UnsafeMutablePointer&GT;&#39;) 我尽可能地研究,但没有任何效果。请帮忙
答案 0 :(得分:2)
Swift 4
class ViewController: UIViewController {
@IBOutlet weak var label: UILabel!
override func viewDidLoad() {
super.viewDidLoad()
let text = "|東京都《とうきょうと》"
label.attributedText = text.attributedStringWithRuby()
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
}
extension String {
func attributedStringWithRuby() -> NSMutableAttributedString {
// "|": ルビを振る対象の文字列を判定し区切る為の記号(全角). ルビを振る文字列の先頭に挿入する
// "《》": ルビを振る対象の漢字の直後に挿入しルビを囲う(全角)
let attributed =
self.replace(pattern: "(|.+?《.+?》)", template: ",$1,")
.components(separatedBy: ",")
.map { x -> NSAttributedString in
if let pair = x.find(pattern: "|(.+?)《(.+?)》") {
let string = (x as NSString).substring(with: pair.range(at: 1))
let ruby = (x as NSString).substring(with: pair.range(at: 2))
var text = [.passRetained(ruby as CFString) as Unmanaged<CFString>?, .none, .none, .none]
let annotation = CTRubyAnnotationCreate(.auto, .auto, 0.5, &text[0])
return NSAttributedString(
string: string,
attributes: [kCTRubyAnnotationAttributeName as NSAttributedStringKey: annotation])
} else {
return NSAttributedString(string: x, attributes: nil)
}
}
.reduce(NSMutableAttributedString()) { $0.append($1); return $0 }
return attributed
}
func find(pattern: String) -> NSTextCheckingResult? {
do {
let re = try NSRegularExpression(pattern: pattern, options: [])
return re.firstMatch(
in: self,
options: [],
range: NSMakeRange(0, self.utf16.count))
} catch {
return nil
}
}
func replace(pattern: String, template: String) -> String {
do {
let re = try NSRegularExpression(pattern: pattern, options: [])
return re.stringByReplacingMatches(
in: self,
options: [],
range: NSMakeRange(0, self.utf16.count),
withTemplate: template)
} catch {
return self
}
}
}
由于苹果公司在iOS 11中的错误,这个解决方案毫无用处。
Code Result: As you can see, there isn't furigana
我在一个月前向Apple发出此错误的信号,但我还没有回答。
一个用户建议覆盖uilabel的方法drawText,但是存在很多问题,因为uilabel所做的每一个文本管理都没有。
无论如何,如果你想看到他的解决方案,这就是他的回答https://stackoverflow.com/a/47377024/3489707
请,如果您找到解决方案,请发布。这非常重要
答案 1 :(得分:0)
不是一个完整的答案,但这是我在Swift 4中使用ruby的代码中的一个简短摘要-可以清除,但可能是一个有价值的代码示例,因为要在这些函数上查找资源非常困难:
let annotationAttribs: [AnyHashable: Any] = [
kCTRubyAnnotationSizeFactorAttributeName: rubySizeFactor,
kCTRubyAnnotationScaleToFitAttributeName: true,
]
let annotation = CTRubyAnnotationCreateWithAttributes(
alignment, .auto, CTRubyPosition.before, ruby as CFString, annotationAttribs as CFDictionary)
let attribs: [NSAttributedStringKey: Any] = [
NSAttributedStringKey(kCTRubyAnnotationAttributeName as String): annotation, //.takeUnretainedValue(),
NSAttributedStringKey("RubyText"): ruby,
]
return NSAttributedString(
string: string,
attributes: attribs)
答案 2 :(得分:-1)
我找到了一个很好的解决方案
Swift 4.2
此解决方案是对预览答案的更新,可以让您编写日语句子,并使用一种模式可以显示带有假名的句子。
在此解决方案中,您使用3个String扩展名
func find(pattern: String) -> NSTextCheckingResult? {
do {
let findRubyText = try NSRegularExpression(pattern: pattern, options: [])
return findRubyText.firstMatch(
in: self,
options: [],
range: NSMakeRange(0, self.utf16.count))
} catch {
return nil
}
}
func replace(pattern: String, template: String) -> String {
do {
let replaceRubyText = try NSRegularExpression(pattern: pattern, options: [])
return replaceRubyText.stringByReplacingMatches(
in: self,
options: [],
range: NSMakeRange(0, self.utf16.count),
withTemplate: template)
} catch {
return self
}
}
func rubyAttributedString(font: UIFont, textColor: UIColor) -> NSMutableAttributedString {
let attributed =
self.replace(pattern: "(|.+?《.+?》)", template: ",$1,")
.components(separatedBy: ",")
.map { x -> NSAttributedString in
if let pair = x.find(pattern: "|(.+?)《(.+?)》") {
let baseText = (x as NSString).substring(with: pair.range(at: 1))
let ruby = (x as NSString).substring(with: pair.range(at: 2))
let rubyAttribute: [AnyHashable: Any] = [
kCTRubyAnnotationSizeFactorAttributeName: 0.5,
kCTForegroundColorAttributeName: textColor
]
let annotation = CTRubyAnnotationCreateWithAttributes(.auto, .auto, .before, ruby as CFString, rubyAttribute as CFDictionary)
return NSAttributedString(
string: baseText,
attributes: [.font: font,
.foregroundColor: textColor,
kCTRubyAnnotationAttributeName as NSAttributedString.Key: annotation])
} else {
return NSAttributedString(
string: x,
attributes: [.font: font,
.foregroundColor: textColor]
)
}
}
.reduce(NSMutableAttributedString()) { $0.append($1); return $0 }
return attributed
}
此扩展允许您创建一个NSAttributed字符串以提供给标签
Great solution written in Japanese but it possible to download the example project