【问题标题】:Android - How do you efficiently load a large amount of text in a TextView?Android - 如何有效地在 TextView 中加载大量文本?
【发布时间】:2019-07-22 18:34:13
【问题描述】:

我正在编写一个 Android 应用程序,它读取单个文本文件并将其显示在 TextView 上。

我现在正在做的是将整个文件读入字符串(使用BufferedReaderStringBuilder)并使用setText(string) 将其显示在TextView 上。一个 700KB 的文本文件大约需要 2 到 3 秒才能显示在屏幕上。

但我使用了市场上的其他一些电子书阅读器,它们几乎可以立即显示相同的文本。有谁知道我怎么能做到这一点?

谢谢。

编辑:很多人建议使用 ListView,但它不适用于我的特殊情况。这是来自我对其中一个答案的回复: ...[ListView] 对我不起作用有几个原因。 (1) 为了使 Listview 看起来像一个 TextView,我们必须将文本分解为换行符。如果我加载一个大段落,它与加载 TextView 一样慢。 (2) 由于 ListView 只测量屏幕上的项目,我无法提前知道整个文本的总“页数”或“高度”。

【问题讨论】:

    标签: java android textview paging android-view


    【解决方案1】:

    本质上,关键是只在需要时才加载需要的数据。一种方法是将每个段落放入它自己的 TextView 中,该 TextView 放入 ListAdapter 中,而 ListAdapter 又包含在 ListView 中。必须设置某种索引,以便每个段落都知道在数据文件中的何处查找。此界面将允许您仅在需要时加载所需的内容。您的列表适配器看起来像这样(此代码不完整,但它至少应该让您知道应该做什么):

    class ParagraphAdapter extends ListAdapter{
    ArrayList<Integer> mLocations; // Somewhere define this to your locations, I'll leave that for you to figure out
    protected View getView(int position,View convertView, ViewGroup parent)
    {
      mLocations.get(position); // Read the file starting at this position, until the next value
      String text; // This is the output of the above
      TextView tv=new TextView(context);
      tv.setText(parent.getContext());
    }
    }
    

    值得注意的是,亚马逊为 Kindle 应用程序使用了分页系统。如果您有该应用程序,您可以在每个页面的底部看到您所在的部分。每个“页面”的长度可能更接近一个句子左右。然后只需获取正确的页面即可,这可以很快完成。

    【讨论】:

    • 我终于有时间来解决这个问题,但由于某些原因,这个解决方案对我不起作用。 (1) 为了使 Listview 看起来像一个 TextView,我们必须将文本分解为换行符。如果我加载一个大段落,它与加载 TextView 一样慢。 (2) 由于 ListView 只测量屏幕上的项目,我无法提前知道整个文本的总“页数”或“高度”。
    【解决方案2】:

    补充@PearsonArtPhoto 所说的话 -

    我建议您实现某种分页机制,将您的文本分成页面。
    您应该做的是根据假设每页 N + M 个字符来拆分文本。
    N = 固定字符数。
    M = 从 N 到最近的行尾字符的字符数(所以你不会看到最后一个 线被“切割”)。
    我建议,如果您的 android 设备允许您将其保存在“内存中” -
    这样做,
    并且不要尝试从一页接一页的文件中获取它,而是从“内存中”结构中获取 - 这将提高性能。
    一旦您滚动并意识到您需要获取下一页,请从“内存中”结构中获取它。

    【讨论】:

      【解决方案3】:

      您可以将 Jetpack 中的 Android Paging Library 与自定义 View 或 RecyclerView 一起使用

      https://developer.android.com/topic/libraries/architecture/paging

      1. 实现提供数据范围列表的 DataSource 抽象
      2. 实现提供真实数据(来自数据库、网络、文件等)的存储抽象
      3. 使用 RecyclerView 和 Adapter 显示数据

      可在此处找到显示大文件内容的示例应用 https://github.com/YablokovDmitry/FileView

      【讨论】:

        【解决方案4】:

        Lucas Rocha 为此构建了一个名为 Smoothie 的不错的库。

        http://lucasr.org/2012/04/05/performance-tips-for-androids-listview/

        在这些 Android listview 性能提示的末尾,有一个关于 Smoothie 的解释链接,最后你会在 github 上找到可用的库。

        最初描述用于加载图像,该方法也适用于加载文本。

        【讨论】:

        • 欢迎来到 SO!考虑通过演示如何应用您为其提供了手头问题链接的库来提高答案的质量并帮助其独立(即如果链接不再有效)。
        【解决方案5】:

        您必须考虑是否使用了正确的组件。 也许阅读行并将它们放入列表视图会更好。

        试试

        List<String> lines; 
        listview.adapter(new ArrayAdapter<String>(...,lines));
        

        而且很多时候,您所看到的(外观和感觉)并不像您想象的那样。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2011-10-17
          • 1970-01-01
          • 1970-01-01
          • 2020-08-11
          • 2011-07-22
          相关资源
          最近更新 更多