3

I know this question has been asked before but I have a little different situation.

I'm trying to call to loadHTMLString(_ baseURL:) on WKWebview and my baseURL is in the AppData/Documents directory.

I need the HTMLstring to load and it needs to use the images in that directory. the HTMLstring is not located anywhere, I download the string parse it, modify it and load it.

As I understand I can't do that because of some sort of security issue (it worked great on UIWebview), so the HTMLstring is loaded but the images and CSS are not.

Also, I can't call for loadFileURL(_, allowingReadAccessTo:) because I don't have a file I have an HTMLstring and can't save it to file just before the call, because of my own security issues.

My code is huge and has a lot of complexity I would like to achieve loading images in the most painless way.

Does anybody have an idea?

ozd
  • 1,194
  • 10
  • 34
  • 1
    ozd, did you find a solution? I haven't been able to get local images from Documents directory to show using loadHTMLString. (Works on simulator for me, but not on device.) A workaround is likely to base64 encode image data and add to html, though it's not a great solution is some cases (e.g. I still need to get local videos working also). – Ernie Thomason Mar 27 '20 at 10:16

2 Answers2

2

I am not sure the source HTML code you put it where. I assume you are placing it in the Bundle. Here is my idea.

In the HTML file for the image tag. We should do like this template.

<image src="{xxx}" ....>

Then in the iOS code. We will replace the src by the image path and load into the WKWebview:

// make sure you have the image name and extension (for demo purposes, I'm using "myImage" and "png" for the file "myImage.png", which may or may not be localized)
NSString *imageFileName = @"myImage";
NSString *imageFileExtension = @"png";

// load the path of the image in the main bundle (this gets the full local path to the image you need, including if it is localized and if you have a @2x version)
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *imagePath = [documentsDirectory stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.%@", imageFileName, imageFileExtension]];

// generate the html tag for the image (don't forget to use file:// for local paths)
NSString *imgFilePath = [NSString stringWithFormat:@"file://%@", imagePath];

// Replace an imagepath
NSString *path = [[NSBundle mainBundle] pathForResource:@"filename" ofType:@"html"];
NSString *html = [[NSString alloc] initWithContentsOfFile:path encoding:NSUTF8StringEncoding error:nil];
html = [html stringByReplacingOccurrencesOfString:@"{xxx}" withString:imgFilePath];


// Folder html url
NSString *destinationHTMLFolder = [[NSBundle mainBundle] pathForResource:@"myhtml" ofType:@""];
NSURL *destination = [NSURL fileWithPath: destinationHTMLFolder]

[self.webView loadHTMLString:html baseURL:destination];  

Note: Please make sure the baseURL is pointing to the HTML folder. It should be a "Create folder references" option at the time you add the HTML source code into the Xcode.

Duc Nguyen
  • 168
  • 2
  • 11
  • I'm not sure... can it work with multiple images? Also, why would this work? isn't the problem that prevents it to read the file in the first place will prevent the image from loading? also, I need to use CSS files from that directory... you know if it will work on CSS as well? – ozd Feb 02 '20 at 12:15
  • Likes the code concept. You can also replace the image path in the CSS file as well. – Duc Nguyen Feb 02 '20 at 23:52
  • 1
    Did you test it with WKWebview? with sources on the Document folder? because this is not working for me. Also, I get the HTML dynamically from a server and it is encrypted so I download the file, get its content, turn it into HTML in my code and only then load the HTML in my webView. so I don't have an HTML file saved anywhere. – ozd Feb 03 '20 at 11:12
2

I wish I had a better answer and if anybody has a better answer I will gladly accept it. I ended up moving my files to the temp directory :( I've used this -

extension FileManager
{
    func copyToTemporaryDirectory(itemIn itemURL: URL) -> URL?
    {
        let tempDirectoryURL    = URL(fileURLWithPath: NSTemporaryDirectory())
        let fileName            = itemURL.lastPathComponent
        let copyURL             = tempDirectoryURL.appendingPathComponent(fileName)
        let fileManager         = FileManager.default

        do {

            if fileManager.fileExists(atPath: copyURL.path)
            {
                try fileManager.removeItem(at: copyURL)
            }

            try FileManager.default.copyItem(at: itemURL, to: copyURL)

            return copyURL

        }
        catch let error
        {
            logger.debug("copyItem error: \(error.localizedDescription)")
            return nil
        }
    }
}

and then loadHtmlString with the URL to this directory. from this directory, WKWebview is allowed to get everything.

ozd
  • 1,194
  • 10
  • 34