Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Viewport meta tag ignored in Android 4.4 WebView

I have an App/WebApp that runs on Android and IOS. I deploy it both as a WebApp and a native PhoneGap app on IOS and Android. I build the native apps with PhoneGap Build. The tablet UI is designed for an internal pixel width of 768 which works fine on iPad and iPad Mini. For Nexus (601px wide in portrait) I fake it by setting the viewport width to 768px and setting the scaling as:

var gViewportScale = (Math.min(window.screen.width, window.screen.height) / window.devicePixelRatio) / 768;

if (gViewportScale >= 1) {
    document.getElementById("viewport").content
        = "width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=no";
} else {
    document.getElementById("viewport").content
        = "width=768, initial-scale=" + gViewportScale + ", minimum-scale=" + gViewportScale + ", maximum-scale=" + gViewportScale + ", user-scalable=yes";
}

This mimics the iPad Mini behavior. This worked fine up until several months ago. I think this may have broken when I upgraded to Android 4.4 with the change to Chromium. Now the active area for the Android PGB native App is wider than the display. The WebApp continues to display properly in Android Chrome (33.0.1750.136) as it did before (i.e. it fills the display width in portrait). Also works fine as a native App or WebApp in IOS.

I've tried several alternatives and all the current versions of PGB and near as I can tell the Android WebView is ignoring the viewport meta tag with PhoneGap but not on Chrome. It certainly seems like an Android bug that it works on one and not the other.

I've asked this question in the PhoneGap support community and so far no good answers. I thought I'd try here. Of course, I could have separate CSS for Nexus, but true scaling of widths and fonts would be better.

like image 592
srkleiman Avatar asked Mar 04 '14 02:03

srkleiman


2 Answers

You need to set webView.getSettings().setUseWideViewPort(true); else WebView will ignore the meta tag

like image 116
Dori Avatar answered Oct 11 '22 23:10

Dori


I have a workaround that doesn't fix the fact that the viewport tag is ignored, but it solves the original viewport scaling problem in a manner that's probably better than playing with the viewport tag.

Inspired by: Dynamic viewport resizing - Phonegap ignores viewport

and monaca: https://github.com/monaca/monaca.js

I used a fixed viewport tag content:

width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=no

and then use zoom, which Android and Chrome apparently support:

/*
 * Make sure that the device is scaled so that it is at least minWidth px in width
 * in any orientation. This is done by setting the zoom appropriately.
 * Right now, we only need this on Android, which supports zoom.
 * Plan B is to use transforms with scale and transform-origin.
 */
function setupScale (minWidth) {
    var viewWidth = Math.max(document.documentElement.clientWidth, window.innerWidth);
    var viewHeight = Math.max(document.documentElement.clientHeight, window.innerHeight);
    var portWidth = Math.min(viewWidth, viewHeight);
    var landWidth = Math.max(viewWidth, viewHeight);
    var fixScale = function () {
        if (Math.abs(window.orientation) != 90) {
            // portrait
            document.body.style.zoom = portWidth / minWidth;
        } else if (landWidth < minWidth) {
            // landscape, but < minWidth
            document.body.style.zoom = landWidth / minWidth;
        } else {
            // landscape >= minWidth. Turn off zoom.
            // This will make things "larger" in landscape.
            document.body.style.zoom = 1;
        }
    };

    if (gPortWidth >= minWidth) {
        return;     // device is greater than minWidth even in portrait.
    }
    fixScale();                             // fix the current scale.       
    window.onorientationchange = fixScale;  // and when orientation is changed
}

For my app, it lets me set the minimum width of the webpage as 768. Which is the same as the iPad (Mini and regular). On the Nexus 7 which is reports screen width of 601px, I can use the same CSS as iPad.

like image 33
srkleiman Avatar answered Oct 11 '22 23:10

srkleiman