1
    2
    3
    4
    5
    6
    7
    8
    9
   10
   11
   12
   13
   14
   15
   16
   17
   18
   19
   20
   21
   22
   23
   24
   25
   26
   27
   28
   29
   30
   31
   32
   33
   34
   35
   36
   37
   38
   39
   40
   41
   42
   43
   44
   45
   46
   47
   48
   49
   50
   51
   52
   53
   54
   55
   56
   57
   58
   59
   60
   61
   62
   63
   64
   65
   66
   67
   68
   69
   70
   71
   72
   73
   74
   75
   76
   77
   78
   79
   80
   81
   82
   83
   84
   85
   86
   87
   88
   89
   90
   91
   92
   93
   94
   95
   96
   97
   98
   99
  100
  101
  102
  103
  104
  105
  106
  107
  108
  109
  110
  111
  112
  113
  114
  115
  116
  117
  118
  119
  120
  121
  122
  123
  124
  125
  126
  127
  128
  129
  130
  131
  132
  133
  134
  135
  136

content / public / android / java / src / org / chromium / content_public / browser / HostZoomMap.java [blame]

// Copyright 2021 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

package org.chromium.content_public.browser;

import androidx.annotation.NonNull;

import org.chromium.content.browser.HostZoomMapImpl;

import java.util.Map;

/** Implementations of various static methods related to page zoom. */
public class HostZoomMap {
    // Preset zoom factors that the +/- buttons can "snap" the zoom level to if user chooses to
    // not use the slider. These zoom factors correspond to the zoom levels that are used on
    // desktop, i.e. {0.50, 0.67, ... 3.00}, excluding the smallest/largest two, since they are
    // of little value on a mobile device.
    public static final double[] AVAILABLE_ZOOM_FACTORS =
            new double[] {
                -3.80, -2.20, -1.58, -1.22, -0.58, 0.00, 0.52, 1.22, 1.56, 2.22, 3.07, 3.80, 5.03,
                6.03
            };

    // The value of the base for zoom factor, should match |kTextSizeMultiplierRatio|.
    public static final float TEXT_SIZE_MULTIPLIER_RATIO = 1.2f;

    // The current |fontScale| value from Android Configuration. Represents user font size choice.
    // The system font scale acts like the "zoom level" of this component. For the default
    // setting, |fontScale|=1.0; for {Small, Large, XL} the values are {0.85, 1.15, 1.30}.
    // This will be transparently taken into account. If a user has the system font set to
    // XL, then Page Zoom will behave as if it is at 130% while displaying 100% to the user.
    private static float sSystemFontScale = 1.0f;

    // Private constructor to prevent unwanted construction.
    private HostZoomMap() {}

    /**
     * Set a new zoom level for the given web contents.
     * @param webContents   WebContents to update
     * @param newZoomLevel  double - new zoom level
     */
    public static void setZoomLevel(@NonNull WebContents webContents, double newZoomLevel) {
        assert !webContents.isDestroyed();

        // Just before sending the zoom level to the backend, we will take into account the system
        // level setting. We only do this here and not when applying the default values chosen in
        // the settings flow so that if the user changes their OS-level setting, the Chrome setting
        // will continue to display the same value, but adjust accordingly. For example, if the user
        // chooses 150% zoom in settings with font set to XL, then really that choice is 195%. If
        // the user then switches to default |fontScale|, we would still want the value to be 150%
        // shown to the user, and not the 195%.
        HostZoomMapImpl.setZoomLevel(
                webContents,
                newZoomLevel,
                HostZoomMapImpl.adjustZoomLevel(newZoomLevel, sSystemFontScale));
    }

    /** Get the current system font scale */
    public static float getSystemFontScale() {
        return sSystemFontScale;
    }

    /**
     * Set the current system font scale
     * @param newSystemFontScale   float, new value.
     */
    public static void setSystemFontScale(float newSystemFontScale) {
        sSystemFontScale = newSystemFontScale;
    }

    /**
     * Get the current zoom level for a given web contents.
     * @param webContents   WebContents to get zoom level for
     * @return double       current zoom level
     */
    public static double getZoomLevel(@NonNull WebContents webContents) {
        assert !webContents.isDestroyed();

        // Just before returning a zoom level from the backend, we must again take into account the
        // system level setting. Here we need to do the reverse operation of the above, effectively
        // divide rather than multiply, so we will pass the reciprocal of |sSystemFontScale|.
        return HostZoomMapImpl.adjustZoomLevel(
                HostZoomMapImpl.getZoomLevel(webContents), (float) 1 / sSystemFontScale);
    }

    /**
     * Get the zoom levels for all hosts.
     * @param browserContextHandle BrowserContextHandle to get zoom level for.
     * @return  HashMap<String, Double> map containing the host name as a string to the zoom factor
     *         (called zoom level on the c++ side) as a double.
     */
    public static Map<String, Double> getAllHostZoomLevels(
            BrowserContextHandle browserContextHandle) {
        return HostZoomMapImpl.getAllHostZoomLevels(browserContextHandle);
    }

    /**
     * Set the zoom level to the given level for the given host.
     * @param host  host to set zoom level for.
     * @param level new zoom level (as a zoom factor as described in PageZoomUtils.java).
     * @param browserContextHandle  BrowserContextHandle to set zoom level for.
     */
    public static void setZoomLevelForHost(
            BrowserContextHandle browserContextHandle, String host, double level) {
        HostZoomMapImpl.setZoomLevelForHost(browserContextHandle, host, level);
    }

    /**
     * Set the default zoom level for a given browser context handle (e.g. Profile).
     * @param context       BrowserContextHandle to update default for.
     * @param newDefaultZoomLevel   double, new default value.
     */
    public static void setDefaultZoomLevel(
            BrowserContextHandle context, double newDefaultZoomLevel) {
        HostZoomMapImpl.setDefaultZoomLevel(context, newDefaultZoomLevel);
    }

    /**
     * Returns true when the field trial param to adjust zoom for OS-level font setting is
     * true, false otherwise.
     * @return bool True if zoom should be adjusted.
     */
    public static boolean shouldAdjustForOSLevel() {
        return HostZoomMapImpl.shouldAdjustForOSLevel();
    }

    /**
     * Get the default zoom level for a given browser context handle (e.g. Profile).
     * @param context       BrowserContextHandle to get default for.
     * @return double       default zoom level.
     */
    public static double getDefaultZoomLevel(BrowserContextHandle context) {
        return HostZoomMapImpl.getDefaultZoomLevel(context);
    }
}