Android 将 ViewPager 的内容转换为位图
Android convert contents of ViewPager to Bitmap
我有一个显示一系列图表的 ViewPager。我想将用户看到的 ViewPager 的内容转换为可以共享的位图。我已经实现了这一点,但如果系列中有多个图表,它并不总是采用当前显示的图表。通常它取最右边的一个,也就是索引最高的那个(例如,如果有 3 个项目,则为 2)。有的时候是最左边的那个,我一直没弄明白是哪一个的情况。
我是一名业余开发人员,我怀疑我遗漏了一些有关 Viewpager 工作原理的基本信息...
如何将显示的当前 viewpager 项目的内容转换为位图?
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();
}
}
我有一个显示一系列图表的 ViewPager。我想将用户看到的 ViewPager 的内容转换为可以共享的位图。我已经实现了这一点,但如果系列中有多个图表,它并不总是采用当前显示的图表。通常它取最右边的一个,也就是索引最高的那个(例如,如果有 3 个项目,则为 2)。有的时候是最左边的那个,我一直没弄明白是哪一个的情况。
我是一名业余开发人员,我怀疑我遗漏了一些有关 Viewpager 工作原理的基本信息...
如何将显示的当前 viewpager 项目的内容转换为位图?
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();
}
}