WebView获取最大滚动宽度

2024-04-30

大家好,我正在创建 epub 阅读器并在 android webview 中加载这本书 并且还使 webview 水平移动参考this https://stackoverflow.com/questions/36617345/use-horizontal-scroll-in-android-webview/36628228?noredirect=1#comment67688154_36628228但现在我想让 webview 像页面一样移动,所以我想这样做 1.计算总水平滚动宽度和屏幕宽度,然后将它们相除以获得总页数 2.锁定webview的滚动,当用户滑动时,将webview的滚动设置为screenwidth*swipeCount

现在的问题是,当我尝试获取totalHorizo​​ntalScrollWidth时,它给出了屏幕宽度,我尝试了这些方法,但都给出了相同的结果

第一种方法

    ViewTreeObserver vto = webView.getViewTreeObserver();
    vto.addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
        @Override
        public void onGlobalLayout() {
            webView.getViewTreeObserver().removeGlobalOnLayoutListener(this);

            Log.e("ScrollWidth",""+webView.getMeasuredWidth());
            Toast.makeText(getApplicationContext(), "new Width is"+webView.getMeasuredWidth(), Toast.LENGTH_SHORT).show();
        }
    });

返回 480 屏幕宽度

和第二种方法

public class WebViewWidth extends WebView {
public WebViewWidth(Context context) {
    super(context);
}
public WebViewWidth(Context context, AttributeSet attrs) {
    super(context, attrs);
}


public int getContentWidth()
{
    return this.computeHorizontalScrollRange();
}
public int getContentHeight()
{
    return this.computeVerticalScrollRange();
}
}

并使用此 webView 来获取computeHorizo​​ntalScrollRange,如下所示

private class MyWebViewClient extends WebViewClient {

private Context mContext;


public MyWebViewClient(Context context) {
    this.mContext = context;
}
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {

    return true;
}

@Override
public void onPageFinished(WebView view, String url) {
    mProgressDialog.dismiss();

    final WebView myWebView = (WebView) view;



    String varMySheet = "var mySheet = document.styleSheets[0];";

    String addCSSRule = "function addCSSRule(selector, newRule) {"
            + "ruleIndex = mySheet.cssRules.length;"
            + "mySheet.insertRule(selector + '{' + newRule + ';}', ruleIndex);"

            + "}";

    String insertRule1 = "addCSSRule('html', 'padding: 0px; height: "
            + (myWebView.getMeasuredHeight() / mContext.getResources().getDisplayMetrics().density)
            + "px; -webkit-column-gap: 0px; -webkit-column-width: "
            + myWebView.getMeasuredWidth() + "px;')";


    myWebView.loadUrl("javascript:" + varMySheet);
     myWebView.loadUrl("javascript:" + addCSSRule);
    myWebView.loadUrl("javascript:" + insertRule1);


    super.onPageFinished(view, url);
 int widthis =  webView.getContentWidth();

    Toast.makeText(getApplicationContext(), "Width is"+widthis, Toast.LENGTH_SHORT).show();
    Log.i("WidthTotoal Scroll", ""+widthis);

 }
 }

即使这样,结果也是 480,即屏幕尺寸

我也遇到过这个脚本,但不知道如何从这个脚本获取值到android

 String js = ""+
    "var desiredHeight;"+
   " var desiredWidth;"+
   " var bodyID = document.getElementsByTagName('body')[0];"+
   " totalHeight = bodyID.offsetHeight;"+
    "pageCount = Math.floor(totalHeight/desiredHeight) + 1;"+
   " bodyID.style.padding = 10;"+ //(optional) prevents clipped letters around the edges
  "  bodyID.style.width = desiredWidth * pageCount;"+
   " bodyID.style.height = desiredHeight;"+
   " bodyID.style.WebkitColumnCount = pageCount;"; 

有人请帮助我获得 webview 的最大水平滚动宽度或一些替代方法来获得像翻页这样的效果。


我想我已经很晚了但是感谢this https://stackoverflow.com/a/9165698我能够在 WebView 中实现平滑的水平滑动动画。

回到你最初的问题,你想获得 html 页面的总宽度,在我的解决方案中我使用WebChrome客户端 onJsAlert()可以从 javascript 获取返回值的方法。我使用这种方法来获取水平页数。

In my MainActivity.java

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
        WebView.setWebContentsDebuggingEnabled(true);
    }
    wv = (HorizontalWebView) findViewById(R.id.web_view);
    wv.getSettings().setJavaScriptEnabled(true);
    wv.setWebViewClient(new WebViewClient() {

        public void onPageFinished(WebView view, String url) {
            injectJavascript();
        }
    });

    wv.setWebChromeClient(new WebChromeClient() {
        @Override
        public boolean onJsAlert(WebView view, String url, String message, JsResult result) {
            int pageCount = Integer.parseInt(message);
            wv.setPageCount(pageCount);
            result.confirm();
            return true;
        }
    });
    wv.loadUrl("file:///android_asset/ch03.html");  
}

private void injectJavascript() {
    String js = "function initialize(){\n" +
            "    var d = document.getElementsByTagName('body')[0];\n" +
            "    var ourH = window.innerHeight;\n" +
            "    var ourW = window.innerWidth;\n" +
            "    var fullH = d.offsetHeight;\n" +
            "    var pageCount = Math.floor(fullH/ourH)+1;\n" +
            "    var currentPage = 0;\n" +
            "    var newW = pageCount*ourW;\n" +
            "    d.style.height = ourH+'px';\n" +
            "    d.style.width = newW+'px';\n" +
            "    d.style.margin = 0;\n" +
            "    d.style.webkitColumnCount = pageCount;\n" +
            "    return pageCount;\n" +
            "}";
    wv.loadUrl("javascript:" + js);
    wv.loadUrl("javascript:alert(initialize())");
}

I use javascript:警报(初始化())执行 javascript 函数,在该函数中返回创建的水平页面的数量。然后我将其传递给自定义 WebView。

水平WebView.java

public class HorizontalWebView extends WebView {
    private float x1 = -1;
    private int pageCount = 0;

    public HorizontalWebView(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {
        switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
                x1 = event.getX();
                break;
            case MotionEvent.ACTION_UP:
                float x2 = event.getX();
                float deltaX = x2 - x1;
                if (Math.abs(deltaX) > 100) {
                    // Left to Right swipe action
                    if (x2 > x1) {
                        turnPageLeft();
                        return true;
                    }

                    // Right to left swipe action
                    else {
                        turnPageRight();
                        return true;
                    }

                }
                break;
        }
        return true;
    }

    private int current_x = 0;

    private void turnPageLeft() {
        if (getCurrentPage() > 0) {
            int scrollX = getPrevPagePosition();
            loadAnimation(scrollX);
            current_x = scrollX;
            scrollTo(scrollX, 0);
        }
    }

    private int getPrevPagePosition() {
        int prevPage = getCurrentPage() - 1;
        return (int) Math.ceil(prevPage * this.getMeasuredWidth());
    }

    private void turnPageRight() {
        if (getCurrentPage() < pageCount - 1) {
            int scrollX = getNextPagePosition();
            loadAnimation(scrollX);
            current_x = scrollX;
            scrollTo(scrollX, 0);
        }
    }

    private void loadAnimation(int scrollX) {
        ObjectAnimator anim = ObjectAnimator.ofInt(this, "scrollX",
                current_x, scrollX);
        anim.setDuration(500);
        anim.setInterpolator(new LinearInterpolator());
        anim.start();
    }

    private int getNextPagePosition() {
        int nextPage = getCurrentPage() + 1;
        return (int) Math.ceil(nextPage * this.getMeasuredWidth());
    }

    public int getCurrentPage() {
        return (int) (Math.ceil((double) getScrollX() / this.getMeasuredWidth()));
    }

    public void setPageCount(int pageCount) {
        this.pageCount = pageCount;
    }
}

您可以找到完整的工作解决方案here https://github.com/GautamChibde/Android-Horizontal-Swipe-WebView

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

WebView获取最大滚动宽度 的相关文章

随机推荐

  • 在设计时存储“记录数组”的最佳方式

    我需要在设计时存储一组数据 以便在运行时构造一组组件的内容 像这样的事情 type TVulnerabilityData record Vulnerability TVulnerability Name string Description
  • Java 递增/递减运算符 - 它们的行为方式是什么,功能是什么?

    开始学习Java已经三天了 我有这个程序 但我不明白其中的代码main方法与 and 运营商 我什至不知道该怎么称呼他们 这些操作员的名字 谁能给我解释一下这是怎么回事 class Example public static void ma
  • 如何将字段从主报表传递到表格元素?

    到目前为止 我使用列标题和详细信息带来生成表格 现在我想使用iReport 4 0 2 中的表格元素 我这样尝试过 iReport 将参数从主报表查询传递到表或列表的数据集查询 https stackoverflow com questio
  • 如何制作Applicative的固定长度向量实例?

    最近了解了推广 决定尝试写向量 LANGUAGE DataKinds GADTs KindSignatures module Vector where data Nat Next Nat Zero data Vector Nat gt gt
  • Python 中的字符串、整数和运算符

    如何在运算中使用算术运算符 由用户作为字符串输入 我可以打印操作本身 但我想打印解决方案 这是我的笨拙尝试 Initialise variables x 2 y 3 Prompt the user for an arithmetic ope
  • Python 在打开套接字时可以选择哪个网络适配器吗?

    运行 python 应用程序的目标计算机将具有三个可用的网络接口 一般来说 所有三个网络都会有很大不同 但是三个网络中的两个可能位于相似的网络上 在下面的示例中 我无法控制 ETH 2 上的目标地址 因为它是预先配置的系统 因此我被迫以编程
  • 如何取消js文件的压缩?

    如何取消通过 webpack 工具缩小的 js 文件 缩小之前 function autoslideSlider next slide trigger click window on load function preloader fade
  • 使用不正确的凭据登录时,Jquery Mobile Rails & Devise 加载页面时出错

    我正在掌握 Rails 3 的窍门 并制作了几个可用的应用程序 我是在 Rails 中使用 javascript 或 jquery 的新手 我有一个使用 Rails 3 2 devise 和 cancan 的工作应用程序 然后我将其转换为使
  • npm - EPERM:Windows 上不允许操作

    I ran npm config set prefix usr local 运行该命令后 当尝试在 Windows 操作系统上运行任何 npm 命令时 我不断收到以下信息 Error EPERM operation not permitte
  • 实体框架,高效的NavigationProperty.OfType查询

    我在使用每表类型 TPT 继承在 EF4 中构造有效查询时遇到问题 我有一个名为Episode 并且每个情节可以有多个事件 有几种不同类型的事件都源自称为Event 我想过滤不包含特定类型事件的所有剧集 Episode有一个导航属性 它是其
  • 用于 C# 和 iPhone 应用程序的 MongoDB

    我正处于设计应用程序的初始阶段 该应用程序将具有用 C 实现的后端 该后端将使用 IIS 上托管的 WCF Web 服务为其他平台提供数据 iPhone 就是其中之一 由于是个人项目 所以想用它来学习MongoDB 我已经知道有社区开发的
  • Android:将视图放置在任意位置

    我一直在尝试将视图放置在任意位置 My aim 覆盖 JPG PNG 的某个矩形 给定坐标与 JPG PNG 相关的 还有一些其他视图 例如图库或一些视频 我不想使用绝对布局 因为它已被弃用 因此 我使用relativelayout 定义一
  • CSS 精灵和 IE6

    IE6 支持 CSS 精灵吗 是的 IE 6 支持精灵 但不支持 24 位 PNG 透明度 我使用这个 css hack 为 IE background image url images sprites icons sprite png b
  • 使用 T-SQL FOR XML PATH 删除空 XML 节点

    我在用着FOR XML PATH从 SQL Server 2008R2 中的表构造 XML XML 必须按如下方式构建
  • 设备重启后 UNUserNotificationCenter 通知

    我一直在网上搜索 看看您安排的通知是否会在设备重新启动后被删除 我发现了不同的意见 所以我开始测试它 这是我注意到的 我安排了 10 分钟后的通知 重新启动手机 没有任何反应 但是 昨天我安排了很多通知 其中一些是当天的 尽管从昨天开始我已
  • 如何在 Web 视图中向下滚动时隐藏 ActionBar/Toolbar

    在 Google Chrome 和 Play 商店中 该应用程序可以在滚动时隐藏操作栏 并允许用户方便地浏览 请帮助我这样做 我已经将 onTouchListener 用于 webview 但它不起作用 mWebView setOnTouc
  • 同一节点的碰撞检测和重叠检测? [第2部分]

    的延续上一个问题 https stackoverflow com questions 71608423 collision detection and overlapping detection in same node 71622366
  • 更改表以给出外键约束

    我有一个表 其中有 2 列 是从两个不同的表复制的 我现在要做的是对列名 email 和 id 给出外键约束 如下所示 ALTER TABLE users role map ADD CONSTRAINT FK users role map
  • Rhino JavaScript 引擎是否有适用于 .NET 的端口

    我在一家同时拥有 Java 和 NET 实现应用程序的公司工作 该应用程序允许最终用户使用脚本自定义处理和业务规则 Java 版本支持 JavaScript 使用犀牛发动机 http www mozilla org rhino NET 应用
  • WebView获取最大滚动宽度

    大家好 我正在创建 epub 阅读器并在 android webview 中加载这本书 并且还使 webview 水平移动参考this https stackoverflow com questions 36617345 use horiz