问题
I'm using the newest version of Xcode
and Swift
.
I have the following code to load an HTML string and use a custom font, I prior imported in Xcode:
let html = """
<html>
<body>
<head>
<style>
@font-face
{
font-family: 'Blastimo';
src: local('Blastimo'), url('Blastimo.ttf') format('truetype');
}
</style>
</head>
<h1 style="font-family:'Blastimo';font-size:50px;">This is my test!</h1>
</body>
</html>
"""
webView.loadHTMLString(html, baseURL: Bundle.main.resourceURL)
The following code allows me to load remote content, e.g. from my web server:
if let url = URL(string: "https://www.example.com") {
let request = URLRequest(url: url)
webView.load(request)
}
But, what I want to reach is: Load remote content, as in second code, but pass my locally stored custom font to this, as in the first code.
Means: I know how to load an HTML string with a locally stored font and I know how to load remote content without a locally stored font. But I don't know how to load remote content with a locally stored font.
I tried:
webView.load(request, baseURL: Bundle.main.resourceURL)
but this isn't working. It throws an error.
I tried so much but without success. My last idea is to get the source code from the remote content, convert it to a string, add font-face
style to it and load it with webView.loadHTMLString
. This will allow me to display the remote content while still being able to load this with webView.loadHTMLString(html, baseURL: Bundle.main.resourceURL)
to pass the locally stored font to it.
Is there really no other way to do this? Is there no way to use my locally stored font when using webView.load(request)
?
回答1:
I found a solution now. Maybe not the best but it's working.
First, I converted the Blastimo.ttf
file to a base64 encoded CSS embedded font with this converter.
This gives me the following (or similar):
@font-face {
font-family: 'Blastimo';
src: url(data:application/x-font-woff;charset=utf-8;base64,HERE_COMES_THE_QUITE_LONG_BASE64_CODE_CREATED_BY_THE_CONVERTER) format('woff');
font-weight: normal;
font-style: normal;
}
I imported/embedded a file called fonts.css
with this code (the code above from the converter) to my Xcode project. Add to targets
should be activated when importing/embedding.
In my ViewController.swift
file I have the following code (e.g. in viewDidLoad()
) to load the remote content and call the functions for the local CSS file:
if let url = URL(string: "https://www.example.com") {
let request = URLRequest(url: url)
webView.load(request)
}
injectToPage()
Additionally, these three functions have to be added somewhere to the ViewController.swift
file:
private func readFileBy(name: String, type: String) -> String {
guard let path = Bundle.main.path(forResource: name, ofType: type) else {
return "Failed to find path"
}
do {
return try String(contentsOfFile: path, encoding: .utf8)
} catch {
return "Unkown Error"
}
}
func injectToPage() {
let cssFile = readFileBy(name: "fonts", type: "css")
let cssStyle = """
javascript:(function() {
var parent = document.getElementsByTagName('head').item(0);
var style = document.createElement('style');
style.innerHTML = window.atob('\(encodeStringTo64(fromString: cssFile)!)');
parent.appendChild(style)})()
"""
let cssScript = WKUserScript(source: cssStyle, injectionTime: .atDocumentEnd, forMainFrameOnly: false)
webView.configuration.userContentController.addUserScript(cssScript)
}
private func encodeStringTo64(fromString: String) -> String? {
let plainData = fromString.data(using: .utf8)
return plainData?.base64EncodedString(options: [])
}
Now, I can use the locally in the app stored font in my WKWebView
although the content is loaded remotely.
In my case, I added this to the (html or php) file, that's loaded remotely from my web server:
<style>
* {
font-family:'Blastimo';
}
</style>
Note:
The file you're loading remotely needs to have <head></head>
element, since the font is injected at the end of this.
回答2:
Another way to use a custom font is to use a converter like this to convert the font file to a .MOBILECONFIG
file. You can then open this .MOBILECONFIG
file on the device and install the font.
来源:https://stackoverflow.com/questions/62732878/xcode-load-custom-locally-stored-font-for-remote-content-in-wkwebview