Android 将 ViewPager 的内容转换为位图

Android convert contents of ViewPager to Bitmap

我有一个显示一系列图表的 ViewPager。我想将用户看到的 ViewPager 的内容转换为可以共享的位图。我已经实现了这一点,但如果系列中有多个图表,它并不总是采用当前显示的图表。通常它取最右边的一个,也就是索引最高的那个(例如,如果有 3 个项目,则为 2)。有的时候是最左边的那个,我一直没弄明白是哪一个的情况。

我是一名业余开发人员,我怀疑我遗漏了一些有关 Viewpager 工作原理的基本信息...

如何将显示的当前 viewpager 项目的内容转换为位图?

graphs as seen by a user

viewpager 设置了一个自定义的 PagerAdaptor,它通过 ViewwModel 从 Room 数据库中获取数据作为 LiveData,对其进行排序,并将其显示为一系列图形。 下面是一些与 ViewPager 和位图相关的代码片段。让我知道是否需要更多信息才能使我的问题有意义。

代码:

 public class ResultsGraphFragment extends Fragment {
      ViewPager viewPager;

      @Override
      public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
           viewPager = root.findViewById(R.id.viewPager);

           //do this when viewpager moved.
           viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
           @Override
           public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {

           }

           @Override
           public void onPageSelected(int position) {
               displayChevrons();
           }

           @Override
           public void onPageScrollStateChanged(int state) {

           }
       });

...

 private void shareImage() {
    Intent i = new Intent(Intent.ACTION_SEND);
    i.setType("image/*");
    ByteArrayOutputStream stream = new ByteArrayOutputStream();
    i.putExtra(Intent.EXTRA_STREAM, getImageUri(getContext(), getBitmapFromView(viewPager)));
    try {
        startActivity(Intent.createChooser(i, getString(R.string.share_description_image_only)));
    } catch (android.content.ActivityNotFoundException ex) {
        ex.printStackTrace();
    }
}

public static Bitmap getBitmapFromView(View view) {
    Bitmap returnedBitmap = Bitmap.createBitmap(view.getWidth(), view.getHeight(),Bitmap.Config.ARGB_8888);
    Canvas canvas = new Canvas(returnedBitmap);
    Drawable bgDrawable =view.getBackground();
    if (bgDrawable!=null)
        bgDrawable.draw(canvas);
    else
        canvas.drawColor(Color.WHITE);
    view.draw(canvas);
    return returnedBitmap;
} 

public Uri getImageUri(Context inContext, Bitmap inImage) {
    ByteArrayOutputStream bytes = new ByteArrayOutputStream();
    inImage.compress(Bitmap.CompressFormat.JPEG, 100, bytes);
    String path = MediaStore.Images.Media.insertImage(inContext.getContentResolver(), inImage, "Title", null);
    return Uri.parse(path);
}

看来我的问题问错了。 ViewPager 不一定知道它在显示什么,这是 PagerAdapter 的工作。

要将我的 ViewPager 项目的内容转换为位图,我需要引用其中正在显示的视图。

我根据 Shadab Ansari 对这个问题的回答找到了我的解决方案:

我在自定义PagerAdapter的“实例化项目”中填充布局后标记了整个视图,然后使用viewPager.findViewWithTag()找到与当前位置对应的视图。

在 PagerAdapter 中:

@NonNull
@Override
public Object instantiateItem(@NonNull ViewGroup container, int position) {
    LayoutInflater layoutInflater = LayoutInflater.from(mContext);
    View itemView = layoutInflater.inflate(R.layout.list_item_result_graph, container, false);
    //tag item view so that the correct graph can be found and shared from ResultsGraphFragment
    itemView.setTag("View"+position);

我的新 shareImage() 方法:

private void shareImage() {
    Intent i = new Intent(Intent.ACTION_SEND);
    i.setType("image/*");
    int currentItem = viewPager.getCurrentItem();
    View v = viewPager.findViewWithTag("View"+currentItem);
    if (v != null) {
        i.putExtra(Intent.EXTRA_STREAM, getImageUri(getContext(), getBitmapFromView(v)));
        try {
            startActivity(Intent.createChooser(i, getString(R.string.share_description_image_only)));
        } catch (android.content.ActivityNotFoundException ex) {
            ex.printStackTrace();
        }
    } else {
        Toast.makeText(this.getContext(), "error sharing image", Toast.LENGTH_SHORT).show();
    }
}