Skip to content

Instantly share code, notes, and snippets.

@jubishop
Created December 7, 2024 03:04
Show Gist options
  • Save jubishop/461f90dc227e7725f4d90e9787d7a1e9 to your computer and use it in GitHub Desktop.
Save jubishop/461f90dc227e7725f4d90e9787d7a1e9 to your computer and use it in GitHub Desktop.
import SwiftUI
struct HTMLText: View {
let html: String
var customColor: Color = .primary
var font: Font = .body
var body: some View {
if let data = html.data(using: .utf8),
let nsAttributedString = try? NSMutableAttributedString(
data: data,
options: [
.documentType: NSAttributedString.DocumentType.html,
.characterEncoding: String.Encoding.utf8.rawValue,
],
documentAttributes: nil
)
{
let modifiedAttributedString = applyCustomStyles(to: nsAttributedString)
let attributedString = AttributedString(modifiedAttributedString)
Text(attributedString)
} else {
Text(html).foregroundStyle(customColor).font(font)
}
}
private func applyCustomStyles(
to nsAttributedString: NSMutableAttributedString
) -> NSAttributedString {
nsAttributedString.enumerateAttributes(
in: NSRange(location: 0, length: nsAttributedString.length)
) { attributes, range, _ in
if attributes.keys.contains(.foregroundColor) {
nsAttributedString.removeAttribute(.foregroundColor, range: range)
}
let fontSize = fontSize(for: font)
let currentFont =
attributes[.font] as? UIFont
?? UIFont.systemFont(ofSize: UIFont.systemFontSize)
let newFont = currentFont.withSize(fontSize)
nsAttributedString.addAttribute(
.font,
value: newFont,
range: range
)
nsAttributedString.addAttribute(
.foregroundColor,
value: UIColor(customColor),
range: range
)
}
return nsAttributedString
}
private func fontSize(for font: Font) -> CGFloat {
let textStyleMapping: [Font: UIFont.TextStyle] = [
.largeTitle: .largeTitle,
.title: .title1,
.title2: .title2,
.title3: .title3,
.headline: .headline,
.subheadline: .subheadline,
.body: .body,
.callout: .callout,
.caption: .caption1,
.caption2: .caption2,
.footnote: .footnote
]
let textStyle = textStyleMapping[font, default: .body]
return UIFont.preferredFont(forTextStyle: textStyle).pointSize
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment