web-dev-qa-db-ja.com

SwiftUI TextでHTMLまたはMarkdownを表示する方法は?

レンダリングされたHTMLまたはMarkdownを表示するようにSwiftUI Textを設定するにはどうすればよいですか?

このようなもの:

Text(HtmlRenderedString(fromString: "<b>Hi!</b>"))

またはMDの場合:

Text(MarkdownRenderedString(fromString: "**Bold**"))

おそらく別のビューが必要ですか?

4
Div

特にテキストビューを使用する必要がない場合。 WKWebViewと単純な呼び出しloadHTMLString()を表示するUIViewRepresentableを作成できます。

import WebKit
import SwiftUI

struct HTMLStringView: UIViewRepresentable {
    let htmlContent: String

    func makeUIView(context: Context) -> WKWebView {
        return WKWebView()
    }

    func updateUIView(_ uiView: WKWebView, context: Context) {
        uiView.loadHTMLString(htmlContent, baseURL: nil)
    }
}

あなたの体で、このオブジェクトを次のように呼び出すだけです:

import SwiftUI

struct Test: View {
    var body: some View {
        VStack {
            Text("Testing HTML Content")
            Spacer()
            HTMLStringView(htmlContent: "<h1>This is HTML String</h1>")
            Spacer()
        }
    }
}

struct Test_Previews: PreviewProvider {
    static var previews: some View {
        Test()
    }
}
2
Tomas Cordoba

パッケージ https://github.com/iwasrobbed/Down を使用して、マークダウン文字列からHTMLまたはMDを生成してから、カスタムUILabelサブクラスを作成し、SwiftUIで使用できるようにすることができます。次の例:

struct TextWithAttributedString: UIViewRepresentable {

    var attributedString: NSAttributedString

    func makeUIView(context: Context) -> ViewWithLabel {
        let view = ViewWithLabel(frame: .zero)
        return view
    }

    func updateUIView(_ uiView: ViewWithLabel, context: Context) {
        uiView.setString(attributedString)
    }
}

class ViewWithLabel : UIView {
    private var label = UILabel()

    override init(frame: CGRect) {
        super.init(frame:frame)
        self.addSubview(label)
        label.numberOfLines = 0
        label.autoresizingMask = [.flexibleWidth, .flexibleHeight]
    }

    required init?(coder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }

    func setString(_ attributedString:NSAttributedString) {
        self.label.attributedText = attributedString
    }

    override var intrinsicContentSize: CGSize {
        label.sizeThatFits(CGSize(width: UIScreen.main.bounds.width - 50, height: 9999))
    }
}

私はそれである程度成功していますが、ラベルサブクラスのフレームを正しく取得できません。多分私はそのためにGeometryReaderを使用する必要があります。

2
blackjacx

SwiftUI専用のマークダウンライブラリを作成しました。

https://github.com/Lambdo-Labs/MDText

貢献してください!

1
Andre Carrera