#java #c# #android #xamarin.android #android-webview
#java #c# #Android #xamarin.android #android-webview
Вопрос:
- Откройте PDF-файл в Webview с помощью документов Google
- Открывайте один и тот же PDF-файл или другой PDF-файл снова и снова.
- Иногда он будет отображать пустую / белую страницу в Android, пока мы снова не обновим веб-страницу 1 или 2 раза.
Я сделал образец в PDF. Ссылка на проект показана ниже:
https://github.com/gopalawasthi123/PdfWebView
Надеюсь, это поможет вам лучше.
public void SetWebView(WebView webview,string externalUrl){
webview.Tag = "webview";
webview.Settings.JavaScriptEnabled = true;
webview.Settings.SupportZoom ();
webview.Settings.SetAppCacheEnabled(true);
webview.Settings.DomStorageEnabled = true;
webview.ZoomOut ();
webview.ZoomIn ();
webview.Settings.BuiltInZoomControls = true;
webview.Settings.LoadWithOverviewMode = true;
webview.Settings.UseWideViewPort = true;
//webview.Settings.SetSupportZoom (true);
webview.Settings.SetPluginState (WebSettings.PluginState.On);
webview.Settings.GetPluginState ();
if (externalUrl.StartsWith("http://") || externalUrl.StartsWith("https://"))
webview.LoadUrl (externalUrl);
webview.SetWebViewClient (new MonkeyWebViewClient (imgViewBack, imgViewForward, imgRefresh));
webview.SetWebChromeClient (new WebChromeClient ());
}
Комментарии:
1. Привет, спасибо, что поделились примером, вы решили эту проблему? Я нашел решение для меня. При необходимости я обновлю ответ 🙂
2. Спасибо, пожалуйста, обновите его. или вы также можете поделиться кодом, если хотите
3. Хорошо, я поделюсь решением 🙂
4. вы получили решение?
5. @HariShankarS Я отметил правильный ответ, вы можете попробовать ответ Микеланджело Пуччи в приведенных ниже ответах, которые будут работать для вас
Ответ №1:
Вы можете перезагрузить страницу, пока она не отобразит PDF таким образом:
public void onPageFinished(WebView view, String url) {
if (view.getTitle().equals(""))
view.reload();
}
Комментарии:
1. здесь вместо получения заголовка вы сравниваете свое условие, используя условие if (view.getContentHeight() == 0), которое предоставит вам точные данные о том, загружена ваша страница или нет.
Ответ №2:
После тестирования второго файла URL-адреса PDF WebView, похоже, не может загрузить большой файл PDF.
Причина:
WebView отображает HTML. Тот факт, что это вообще работает, является взломом — Google преобразует простые PDF-файлы в HTML. Не похоже, что они поддерживают что-то настолько большое. Даже если бы они это сделали, я бы ожидал, что загрузка большой страницы PDF, преобразованной в HTML, будет настолько большой, что я очень сомневаюсь, что вы сможете загрузить ее, не переходя на ООМ. Используйте соответствующую библиотеку PDF, создайте реальный вид рендеринга PDF и убедитесь, что за один раз не отображается больше PDF-файла, чем вам нужно (иначе вы все равно перейдете на ООМ). Другими словами, не полагайтесь на хакерские решения, на которые вам никогда не следовало полагаться в первую очередь.
Решение:
Вам следует попробовать такие альтернативы, какPDF.js запускается локально на вашем устройстве вместо службы, подобной Google Docs preview.(Или сначала загрузите PDF по локальному пути к файлу)
Поместите его в папку с активами и настройте пример:
wv.loadUrl("file:///android_asset/web/viewer.html");
Кроме того, у вас могут возникнуть ситуации с нехваткой памяти. Альтернативой является встроенный просмотрщик, такой как AndroidPdfViewer.
Комментарии:
1. я попробовал оба ваших решения. но эти решения не сработали для меня, если вы откроете этот PDF-файл 9-10 раз, страница вместо этого станет пустой / белой. Также не могли бы вы изменить URL на adobe.com/content/dam/acom/en/devnet/acrobat/pdfs / …
2. @GopalAwasthi Привет, после тестирования нового URL-адреса я обнаружил, что проблема также существует. Предыдущее решение может не полностью решить эту проблему. Это связано с другой причиной. Я обновил ответ.
Ответ №3:
Мы можем решить проблему двумя способами. 1. Одним из них является использование плагина Js.Pdf на стороне сервера. Это, безусловно, решает проблему, но если у нас есть несколько PDF-файлов во фрагменте, это может привести к нехватке памяти, и приложение может выйти из строя. 2. Второй вариант — мы можем рекурсивно вызвать функцию для загрузки webview. Это также вызовет проблему, но с меньшей частотой Ниже приведен код:
private void showPdf(final String imageString) {
pdfView.invalidate();
pdfView.getSettings().setJavaScriptEnabled(true);
pdfView.getSettings().setSupportZoom(true);
pdfView.loadUrl("http://docs.google.com/gview?embedded=trueamp;url=" imageString);
pdfView.setWebViewClient(new WebViewClient() {
boolean checkhasOnPageStarted = false;
@Override
public void onPageStarted(WebView view, String url, Bitmap favicon) {
checkhasOnPageStarted = true;
}
@Override
public void onPageFinished(WebView view, String url) {
if (checkhasOnPageStarted ) {
pdfView.loadUrl(removePdfTopIcon);
} else {
showPdf(imageString);
}
}
});
}
Ответ №4:
У меня была точно такая же проблема, и я обнаружил, что всегда был шанс, что WebView не загрузится при первой попытке загрузки, особенно если PDF был на большей стороне. Приведенный ниже код работает в 100% случаев. Насколько я понимаю для начинающих, он безопасно использует отдельный поток для просмотра и проверки состояния загрузки WebView, повторяя попытку загрузки представления до успешного завершения. Поскольку этот вопрос был опубликован год назад, я обобщил свое решение, чтобы наилучшим образом использовать новых зрителей.
public class WebViewActivity extends AppCompatActivity {
String PDFView;
WebView webView;
String PDFBrowserView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//Get the intended "PDFView"
PDFView = getIntent().getExtras().get("PDFView").toString();
//Have to manually encode (?) the url to display it
try {
PDFView = URLEncoder.encode(PDFView, "UTF-8");
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
//Full display url
PDFBrowserView = "https://docs.google.com/gview?embedded=trueamp;url=" PDFView;
//Initialize a new "WebView" instance
webView = new WebView(WebViewActivity.this);
webView.getSettings().setJavaScriptEnabled(true);
webView.getSettings().setAllowFileAccessFromFileURLs(true);
webView.getSettings().setAllowUniversalAccessFromFileURLs(true);
webView.getSettings().setBuiltInZoomControls(true);
webView.getSettings().setJavaScriptEnabled(true);
webView.getSettings().setPluginState(WebSettings.PluginState.ON);
webView.getSettings().setDomStorageEnabled(true);
webView.getSettings().setLoadWithOverviewMode(true);
webView.getSettings().setUseWideViewPort(true);
//This handles callbacks (?)
webView.setWebChromeClient(new WebChromeClient());
//Call this to load page if page is blank with pdf url until page is not blank
checkPageFinished();
}
public void checkPageFinished() {
//If view is blank:
if (webView.getContentHeight() == 0) {
//Run off main thread to control delay
webView.postDelayed(new Runnable() {
@Override
public void run() {
//Load url into the "WebView"
webView.loadUrl(PDFBrowserView);
}
//Set 1s delay to give the view a longer chance to load before
// setting the view (or more likely to display blank)
}, 1000);
//Set the view with the selected pdf
setContentView(webView);
webView.postDelayed(new Runnable() {
@Override
public void run() {
//If view is still blank:
if (webView.getContentHeight() == 0) {
//Loop until it works
checkPageFinished();
}
}
//Safely loop this function after 1.5s delay if page is not loaded
}, 1500);
}
}
}
Ответ №5:
Есть несколько способов, с помощью которых мы можем определить, правильно ли загружена страница / URL или нет, из onPageFinished()
метода Webview и на основе этого reload()
URL.
Вариант 1: проверить с contentHeight
помощью webview.
override fun onPageFinished(view: WebView?, url: String?) {
if(view?.contentHeight == 0){
view?.reload()
return
}
super.onPageFinished(view, url)
}
Вариант 2: проверить с title
помощью webview.
override fun onPageFinished(view: WebView?, url: String?) {
if(view?.title.isNullOrEmpty()){
view?.reload()
return
}
super.onPageFinished(view, url)
}
Ответ №6:
Протестировано на нескольких устройствах и работает в API 29
в Kotlin
val webSettings: WebSettings = webview.settings
webSettings.javaScriptEnabled = true
webSettings.useWideViewPort = true
webSettings.loadWithOverviewMode = true
webSettings.domStorageEnabled = true
webview.webViewClient = AppWebViewClients()
// val TERM_CONDITION_URL = "http://docs.google.com/gview?embedded=trueamp;url="
// "YOUR_DOC_URL_HERE"
bindind?.webview?.loadUrl(TERM_CONDITION_URL)
и здесь AppWebViewClients
класс
class AppWebViewClients : WebViewClient() {
override fun shouldOverrideUrlLoading(view: WebView, url: String?): Boolean {
view.loadUrl(url)
return true
}
override fun onPageFinished(view: WebView?, url: String?) {
if (view?.contentHeight == 0)
view?.reload();
else {
super.onPageFinished(view, url)
}
}
}
Ответ №7:
Я думаю, вы должны сделать, как показано ниже:
public void onPageFinished(WebView view, String url) {
if (!view.getUrl().equals(url)) {
view.loadUrl(url);
return;
}
}