安卓中WebView文本缩放问题

9
我在Android上有一个文档阅读器项目。主Activity包括一个WebView,文本从html中读取。在顶部选项菜单中包括一个按钮,可以动态增加文本大小(文本换行)。到目前为止一切都很清楚,但是当按下按钮时,文本大小会增加,但所有文本都会向屏幕下方移动。当两次按下按钮时,文本大小会增加,并且所有文本再次向下移动一点。这对于读者来说真的很令人沮丧。读者必须在按下按钮后返回到离开的位置,以便不会失去阅读位置。如何解决这个问题?

问题:

问题:

问题解决后:

问题解决后:

我的WebView的Html内容:

<!DOCTYPE html>

    <head>
        <style type="text/css"> 
            p{} p.x1{} p.x2{} p.x3{} p.x4{} 
            h2.x1{} h2.x2{} h2.x3{} h2.x4{}
        </style>
    </head>

    <body>

        //paragraph-1
        <p class="x1">Title-1</p>
        <p class="x2">Title-2</p>
        <p class="x3">Title-3</p>
        <p class="x4">Title-4</p>
        <p>Text content.</p>


        //paragraph-2
        <h class="x1">Title-1</p>
        <h class="x2">Title-2</p>
        <p>Text content.</p>


        //paragraph-3
        <h class="x3">Title-1</p>
        <h class="x4">Title-2</p>
        <p class="x3">Title-3</p>
        <p>Text content.</p>


        //paragraph-4
        <h class="x2">Title-1</p>
        <p class="x3">Title-2</p>
        <p>Text content.</p>


        //...

    </body>

</html>
4个回答

2
您应该在ListView中使用TextView,并在缩放之前存储顶部列表项的ID,然后在缩放后滚动到存储的列表项。为了实现良好的滚动效果,您应该使用基本的图像缩放效果来隐藏滚动条。

1

我保持文本在屏幕上的想法是存储对于特定 x,y 点在屏幕上显示的任何 "元素" (p、div、img 等) 的引用,更改字体大小,然后将该元素滚动回到屏幕上。

我创建了一个在Android Webview中工作的代码示例:

//Route your onclick handler to our new function
function fontBtnClk() {

  //Store whatever paragraph container is in the middle of the screen
  var currentParagraph = document.elementFromPoint(window.innerWidth/3, window.innerHeight/3);

  //If the above "paragraph selector" selected the whitespace in-between two paragraphs, and stored the parent element instead:
  if(currentParagraph.tagName.toLowerCase()=="body") {

    //Divide by a different number to select the winning paragraph
    currentParagraph = document.elementFromPoint(window.innerWidth/3, window.innerHeight/2);
  }

  //Call your existing font size handler
  increaseFontSize();

  //Move the previous paragraph back onto the screen:
  currentParagraph.scrollIntoView();
}

希望这能解决你的问题!

修改后的问题,您可以查看更多细节。我不明白 "PARENT-ELEMENT-ID" 是什么? - ATES
@ATES 好的,我调整了我的代码以与您的HTML完美执行! - Aaron Gillion
@ATES你在安卓设备上试过吗?JSbin的表现非常完美! - Aaron Gillion
@ATES 我的代码选择页面上接近中间的段落。所以对于非常小的字体,它会跳过。如果您使用window.innerHeight/5(更大的除数),则在桌面计算机上不会跳过。 - Aaron Gillion
Android应用程序可以安装在不同的屏幕尺寸上,因此需要比较智能的脚本。 - ATES

1
我建议使用字体大小增加前后的相对滚动位置来计算用户应该在哪里。这可以通过以下几个步骤完成:
  1. 在更改字体大小之前,存储文本视图的滚动高度和滚动位置。确定滚动高度和滚动位置之间的比率(在0到1之间)
  2. 更改字体大小
  3. 渲染后,测量新的滚动高度
  4. 将新的滚动位置设置为新的滚动高度乘以旧比率。

相关代码片段:

function setSize() {
  var heightBefore = textContainer.scrollHeight;
  var scrollBefore = textContainer.scrollTop;
  var percBefore = scrollBefore / heightBefore;

  textContainer.style.fontSize = fontSize + "px";

  var heightAfter = textContainer.scrollHeight;
  var scrollAfter = textContainer.scrollTop;

  var correctedScrollAfter = Math.floor(heightAfter * percBefore);
  textContainer.scrollTop = correctedScrollAfter;
}

你可以在这里查看一个示例: https://jsfiddle.net/Ln43xxv5/

我必须承认,我现在无法在安卓上进行测试,但我相信一般方向应该是可行的。


我在jsfiddle和Android应用程序上尝试了你的脚本,但没有稳定性。因为段落不会固定在屏幕顶部,当字体增大时它会上下移动。 - ATES
这段代码在数学解法方面非常精确。我喜欢它!但当容器包含不同大小的字体和图像时会发生什么?我认为高度比将无法考虑这些差异。 - Aaron Gillion
没想到这一点,非常有道理!我猜这个解决方案只适用于类似电子书的内容...感谢您的评论。 - user3297291
只有文本内容但不同的字体大小是不可避免的,所以我说没有稳定性。 - ATES

-1
尝试这个:
settings.setDefaultFontSize(50);  //Larger number == larger font size

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接