What is the best approach for handling the following. I have an HTML page with some JavaScript which I load into UIWebview control. I would like to invoke a js function on the page which mutates the DOM, and after the DOM mutation I would like to capture a screenshot of the webpage. The problem I am facing is that the image captured from the UIWebview does not represent the current state of the html page. It represents the state of the DOM prior to the invocation of the [myWebview stringbyevaluatingjavascriptfromstring:@"myHandle.func()"];
from below.
[myWebview stringbyevaluatingjavascriptfromstring:@"myHandle.func()"];
UIGraphicsBeginImageContext(myWebview .bounds.size);
[myWebview .layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *viewImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
I believe that the problem is related to the fact that the Native UI updates are not updated until the end of the current Run Loop. Therefor the UIWebView does not reflect the current state of the DOM at the point of screen capture.
I have managed to get the functionality I seek working via the following two approaches. Calling both immediately after
[myWebview stringbyevaluatingjavascriptfromstring:@"myHandle.func()"];
1.
[self performSelector:@selector(createWebviewImage) withObject:nil afterDelay:0]
where createWebViewImage
simply holds the following logic
UIGraphicsBeginImageContext(myWebview .bounds.size);
[myWebview .layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *viewImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
2.
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_LOW, 0), ^{
// Back to the main thread for a chunk of code
dispatch_sync(dispatch_get_main_queue(), ^{
[self createWebviewImage];
});
});
Theses two methods do work in my small test case although I am extremely apprehensive about using them as I am afraid of a case where they may fail.