NSTextAttachment에 추가된 이미지 색상을 변경할 때 매혹
16472 단어 SwiftNSAttributedStringUILabeliOS
대체로 아래의 느낌으로 실현할 수 있다.
*UIIMage.withRenderingMode(.alwaysTemplate) 생성
* NSTextAttachment 이미지로 설정
* NSMutableAttributedString에 NSAttributedString 적용
*NSMutableAttributedString에서 addAttributedString(u,value:range:) NSAttributedString.Key.foregroundColor를 포인트로 UIColor 설정
이런
let image = UIImage(named: "foo")!
let attributedString = NSMutableAttributedString(string:"")
let templateImage = image.withRenderingMode(.alwaysTemplate)
let textAttachment = NSTextAttachment()
textAttachment.image = templateImage
textAttachment.bounds = CGRect(x: 0, y: 0, width: 20, height: 20)
let attrString = NSAttributedString(attachment: textAttachment)
attributedString.append(attrString)
attributedString.addAttribute(
NSAttributedString.Key.foregroundColor,
value: UIColor.green,
range: NSRange(location: 0, length: attributedString.length))
label.attributedText = attributedString
하지만 나는 몇 번이나 썼어야 할 이 코드에 두 시간 정도 빠져들었다.문제
설정된 UIColor는 전혀 반영되지 않았습니다.
원인
NSMutableAttributedString의 시작이 문자열인 경우에는 문제가 없습니다.
그 결과 NSTextAttachment에서 시작된 상황에서addAttachment를 해도 UIColor는 이미지에 적용되지 않습니다.
NSMutableAttributedString 컨텐츠
"😀text
"text😀"그러면문제없어요.
문제가 있다
문제없다
대책
NSMutableAttributedString의 시작 부분에 문자열(공간)을 추가하여 회피합니다. let image = UIImage(named: "foo")!
let attributedString = NSMutableAttributedString(string:"") // <- ここに入れてもOK
let templateImage = image.withRenderingMode(.alwaysTemplate)
let textAttachment = NSTextAttachment()
textAttachment.image = templateImage
textAttachment.bounds = CGRect(x: 0, y: 0, width: 20, height: 20)
let attrString = NSAttributedString(attachment: textAttachment)
attributedString.append(attrString)
attributedString.insert(NSAttributedString(string: " "), at: 0) // <- これ
attributedString.addAttribute(
NSAttributedString.Key.foregroundColor,
value: UIColor.green,
range: NSRange(location: 0, length: attributedString.length))
label.attributedText = attributedString
이렇게 하면 한 가지 일이 해결될 줄 알았는데 함정이 있을 줄은 생각지도 못했다.
처음에 문자열을 넣어서 시작을 뒤로 하는 문자열은 이미지만 있는 경우보다 베이스라인이 조금 높습니다.
밀집된 레이아웃의 응용 프로그램이라면 위쪽이 끊어지고 아래에 이상한 공간이 생길 수 있다
대체적으로 코드상 매우 메스껍다.
첫 번째는 그림입니다.
문자열로 시작
문제는 회피되었지만, 앞에는 공간 (문자열) 과baseline이 미묘하게 위에 있습니다.
대책
베이스라인에 맞추려고 노력해도 맨 앞에 공간이 있을 수는 없다.
또한 AttributedString의 처리에 의존하여 레이아웃을 하는 것도 앞으로 고통스러운 시선을 보게 될 것이다.
촌스럽지만 그림 자체를 색깔로 덮어쓰는 방법이다.class HogeView {
func fuga() {
let image = UIImage(named: "foo")!
let attributedString = NSMutableAttributedString(string:"")
let templateImage = image.withRenderingMode(.alwaysTemplate)
let textAttachment = NSTextAttachment()
textAttachment.image = templateImage.overray(with: .red)
textAttachment.bounds = CGRect(x: 0, y: 0, width: 20, height: 20)
let attrString = NSAttributedString(attachment: textAttachment)
attributedString.append(attrString)
label.attributedText = attributedString
}
}
extension UIImage {
func overray(with fillColor: UIColor) -> UIImage {
// using scale correctly preserves retina images
UIGraphicsBeginImageContextWithOptions(size, false, scale)
let context: CGContext! = UIGraphicsGetCurrentContext()
assert(context != nil)
// correctly rotate image
context.translateBy(x: 0, y: size.height)
context.scaleBy(x: 1.0, y: -1.0)
let rect = CGRect(x: 0.0, y: 0.0, width: size.width, height: size.height)
// draw tint color
context.setBlendMode(.normal)
fillColor.setFill()
context.fill(rect)
// mask by alpha values of original image
context.setBlendMode(.destinationIn)
context.draw(self.cgImage!, in: rect)
let image = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()
return image!
}
}
결과
감상
글의 첫머리에 아이콘 같은 인상을 주는 경우가 많은 것 같아요.
Reference
이 문제에 관하여(NSTextAttachment에 추가된 이미지 색상을 변경할 때 매혹), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다
https://qiita.com/a_jike/items/5eabc3920f987c24425a
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념
(Collection and Share based on the CC Protocol.)
NSMutableAttributedString의 시작이 문자열인 경우에는 문제가 없습니다.
그 결과 NSTextAttachment에서 시작된 상황에서addAttachment를 해도 UIColor는 이미지에 적용되지 않습니다.
NSMutableAttributedString 컨텐츠
"😀text
"text😀"그러면문제없어요.
문제가 있다
문제없다
대책
NSMutableAttributedString의 시작 부분에 문자열(공간)을 추가하여 회피합니다. let image = UIImage(named: "foo")!
let attributedString = NSMutableAttributedString(string:"") // <- ここに入れてもOK
let templateImage = image.withRenderingMode(.alwaysTemplate)
let textAttachment = NSTextAttachment()
textAttachment.image = templateImage
textAttachment.bounds = CGRect(x: 0, y: 0, width: 20, height: 20)
let attrString = NSAttributedString(attachment: textAttachment)
attributedString.append(attrString)
attributedString.insert(NSAttributedString(string: " "), at: 0) // <- これ
attributedString.addAttribute(
NSAttributedString.Key.foregroundColor,
value: UIColor.green,
range: NSRange(location: 0, length: attributedString.length))
label.attributedText = attributedString
이렇게 하면 한 가지 일이 해결될 줄 알았는데 함정이 있을 줄은 생각지도 못했다.
처음에 문자열을 넣어서 시작을 뒤로 하는 문자열은 이미지만 있는 경우보다 베이스라인이 조금 높습니다.
밀집된 레이아웃의 응용 프로그램이라면 위쪽이 끊어지고 아래에 이상한 공간이 생길 수 있다
대체적으로 코드상 매우 메스껍다.
첫 번째는 그림입니다.
문자열로 시작
문제는 회피되었지만, 앞에는 공간 (문자열) 과baseline이 미묘하게 위에 있습니다.
대책
베이스라인에 맞추려고 노력해도 맨 앞에 공간이 있을 수는 없다.
또한 AttributedString의 처리에 의존하여 레이아웃을 하는 것도 앞으로 고통스러운 시선을 보게 될 것이다.
촌스럽지만 그림 자체를 색깔로 덮어쓰는 방법이다.class HogeView {
func fuga() {
let image = UIImage(named: "foo")!
let attributedString = NSMutableAttributedString(string:"")
let templateImage = image.withRenderingMode(.alwaysTemplate)
let textAttachment = NSTextAttachment()
textAttachment.image = templateImage.overray(with: .red)
textAttachment.bounds = CGRect(x: 0, y: 0, width: 20, height: 20)
let attrString = NSAttributedString(attachment: textAttachment)
attributedString.append(attrString)
label.attributedText = attributedString
}
}
extension UIImage {
func overray(with fillColor: UIColor) -> UIImage {
// using scale correctly preserves retina images
UIGraphicsBeginImageContextWithOptions(size, false, scale)
let context: CGContext! = UIGraphicsGetCurrentContext()
assert(context != nil)
// correctly rotate image
context.translateBy(x: 0, y: size.height)
context.scaleBy(x: 1.0, y: -1.0)
let rect = CGRect(x: 0.0, y: 0.0, width: size.width, height: size.height)
// draw tint color
context.setBlendMode(.normal)
fillColor.setFill()
context.fill(rect)
// mask by alpha values of original image
context.setBlendMode(.destinationIn)
context.draw(self.cgImage!, in: rect)
let image = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()
return image!
}
}
결과
감상
글의 첫머리에 아이콘 같은 인상을 주는 경우가 많은 것 같아요.
Reference
이 문제에 관하여(NSTextAttachment에 추가된 이미지 색상을 변경할 때 매혹), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다
https://qiita.com/a_jike/items/5eabc3920f987c24425a
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념
(Collection and Share based on the CC Protocol.)
let image = UIImage(named: "foo")!
let attributedString = NSMutableAttributedString(string:"") // <- ここに入れてもOK
let templateImage = image.withRenderingMode(.alwaysTemplate)
let textAttachment = NSTextAttachment()
textAttachment.image = templateImage
textAttachment.bounds = CGRect(x: 0, y: 0, width: 20, height: 20)
let attrString = NSAttributedString(attachment: textAttachment)
attributedString.append(attrString)
attributedString.insert(NSAttributedString(string: " "), at: 0) // <- これ
attributedString.addAttribute(
NSAttributedString.Key.foregroundColor,
value: UIColor.green,
range: NSRange(location: 0, length: attributedString.length))
label.attributedText = attributedString
베이스라인에 맞추려고 노력해도 맨 앞에 공간이 있을 수는 없다.
또한 AttributedString의 처리에 의존하여 레이아웃을 하는 것도 앞으로 고통스러운 시선을 보게 될 것이다.
촌스럽지만 그림 자체를 색깔로 덮어쓰는 방법이다.
class HogeView {
func fuga() {
let image = UIImage(named: "foo")!
let attributedString = NSMutableAttributedString(string:"")
let templateImage = image.withRenderingMode(.alwaysTemplate)
let textAttachment = NSTextAttachment()
textAttachment.image = templateImage.overray(with: .red)
textAttachment.bounds = CGRect(x: 0, y: 0, width: 20, height: 20)
let attrString = NSAttributedString(attachment: textAttachment)
attributedString.append(attrString)
label.attributedText = attributedString
}
}
extension UIImage {
func overray(with fillColor: UIColor) -> UIImage {
// using scale correctly preserves retina images
UIGraphicsBeginImageContextWithOptions(size, false, scale)
let context: CGContext! = UIGraphicsGetCurrentContext()
assert(context != nil)
// correctly rotate image
context.translateBy(x: 0, y: size.height)
context.scaleBy(x: 1.0, y: -1.0)
let rect = CGRect(x: 0.0, y: 0.0, width: size.width, height: size.height)
// draw tint color
context.setBlendMode(.normal)
fillColor.setFill()
context.fill(rect)
// mask by alpha values of original image
context.setBlendMode(.destinationIn)
context.draw(self.cgImage!, in: rect)
let image = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()
return image!
}
}
결과
감상
글의 첫머리에 아이콘 같은 인상을 주는 경우가 많은 것 같아요.
Reference
이 문제에 관하여(NSTextAttachment에 추가된 이미지 색상을 변경할 때 매혹), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다
https://qiita.com/a_jike/items/5eabc3920f987c24425a
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념
(Collection and Share based on the CC Protocol.)
Reference
이 문제에 관하여(NSTextAttachment에 추가된 이미지 색상을 변경할 때 매혹), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://qiita.com/a_jike/items/5eabc3920f987c24425a텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)