Here is my code
// create bitmap screen capture
Bitmap bitmap;
View v1 = (View)findViewById(R.id.text);
View rootV = v1.getRootView();
rootV.setDrawingCacheEnabled(true);
bitmap = rootV.getDrawingCache();
rootV.setDrawingCacheEnabled(false);
the nullpointer occurs on bitmap = rootV.getDrawingCache(); and R.id.text is a textView in the layout
I was able to find the answer here. Its because I was calling the method in the onCreate()
Screen capture inside the method onCreate not working in android
Related
I have implemented a video calling feature in our app. There is a button which captures the screenshot of specific view. On video call there a two views Local View and Remote View. These are actually Relative and Frame layouts. In this case i want take screenshot of remote view but it's just giving me a blank image. I think somehow agora video calling not allowing it but there should be any settings or something to disable this but that i have not found yet. here is the code:
Setting up remote video:
mRemoteContainer is a RelativeLayout and mRemoteVideo is VideoCanvas by agora.io
Similarly mLocalContainer is FrameLayout.
private void setupRemoteVideo(int uid) {
ViewGroup parent = mRemoteContainer;
if (parent.indexOfChild(mLocalVideo.view) > -1) {
parent = mLocalContainer;
}
if (mRemoteVideo != null) {
return;
}
SurfaceView view = RtcEngine.CreateRendererView(getBaseContext());
view.setZOrderMediaOverlay(parent == mLocalContainer);
parent.addView(view);
mRemoteVideo = new VideoCanvas(view, VideoCanvas.RENDER_MODE_HIDDEN, uid);
mRemoteVideo.view.setWillNotDraw(false);
mRtcEngine.setupRemoteVideo(mRemoteVideo);
}
This function used to get bitmap from the view
private Bitmap getScreenShotFromView(View v) {
Bitmap screeShoot = null;
try {
screeShoot = Bitmap.createBitmap(v.getMeasuredWidth(), v.getMeasuredHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(screeShoot);
v.draw(canvas);
} catch (Exception e) {
Log.e("GFG", "Failed to capture screenshot because:" + e.getMessage());
}
return screeShoot;
}
I tried function call with both view but getting black or blank image
Bitmap bitmap = getScreenShotFromView(mRemoteVideo.view);
Bitmap bitmap = getScreenShotFromView(mRemoteContainer);
Your help will be really appreciated for me as i stuck on this issue.
By the way I used the same view capturing technique on iOS with swift
and Its working fine.
I have a linear layout that has multiple fields that are to be filled by the user. The fields are to be filled with text or decimal numbers and they are all TextInputLayouts with one date picker. After the user has filled those fields I have a review button which once clicked shows a preview of all the values entered in an image view. I am showing the image by using bitmap and canvas and sending the bitmap as an argument to my material bottom sheet with the following code.
private Bitmap getDailySheetBitmap() {
Bitmap bitmap = Bitmap.createBitmap(completeSheetLinearLayout.getWidth(), completeSheetLinearLayout.getHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bitmap);
Log.d("Bitmap", "bitmap size: "+bitmap.getByteCount());
completeSheetLinearLayout.draw(canvas);
return bitmap;
}
And the code for sending arg is
private void buildBottomSheet(Bitmap bitmap) {
Bundle args = new Bundle();
args.putParcelable("Bitmap", bitmap);
ViewDailySheet viewDailySheet = new ViewDailySheet();
viewDailySheet.setArguments(args);
viewDailySheet.show(getChildFragmentManager(), "DailySheet");
}
The problem is that after the user reviews the fields and changes are made to those fields and when the user again clicks on the review button, the bitmap with the same old values is shown. I have tried recycling bitmap, invalidating the view, requestLayout() and forceLayout() method. But none of it is helping.
This is the code that puts bitmap into image view.This is in bottom sheet dialog fragment.
if (getArguments() != null) {
bitmap = getArguments().getParcelable("Bitmap");
binding.dailySheetImage.invalidate();
binding.dailySheetImage.setImageBitmap(bitmap);
getArguments().clear();
}
What am I doing wrong or missing?
The bitmap only captures what it thinks has changed. If the text field(not the data, just UI) is not changed it will show the same text field value as before. So I refreshed the whole layout as it would re-draw the entire layout by the following code.
private void refreshView() {
completeSheetLinearLayout.setVisibility(View.GONE);
completeSheetLinearLayout.setVisibility(View.VISIBLE);
}
I put this code just before creating the bitmap.
I've a screen in android, which has multiple controls like a Listview and TextView and some buttons to save the record.
If there are more question (say 15) the Listview is displayed in scroll bar as the Listview has fixed length. We have used the below code to take screenshot of the screen on save but when we have more questions in Listview the screen shot is taken only for the record available in the screen. Please suggest how I can take screenshot of all the questions in the Listview when we have more.
Code Used to take screenshot where View is the LinerLayout defined in .xml file
Sample :1
public Bitmap screenShot(View v) {
v.setDrawingCacheEnabled(true);
Bitmap bitmap = Bitmap.createBitmap(v.getDrawingCache());
v.setDrawingCacheEnabled(false);
return bitmap;
}
Sample :2
Bitmap bitmap = Bitmap.createBitmap(v.getMeasuredWidth(), v.getMeasuredHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bitmap);
Drawable bgDrawable = v.getBackground();
if (bgDrawable != null)
bgDrawable.draw(canvas);
else
canvas.drawColor(Color.WHITE);
v.draw(canvas);
I am relatively new to android development and so far I haven't picked up on the purpose of fragments. Anyways, I am trying to create a unique QR code for every user that sign's into my app. This QR code is filled with the user's info which I have retrieved from the database. Now the only trouble I am experiencing is the generation of said qr Code. I have looked through dozens of tutorials but oftentimes they are rendered invalid for my use case or I can't simply get them to work. I have also looked through the ZXING api but that was of not help. I ask of the StackoverFlow community to help with this endeavour and all help is appreciated
There is a slight difference usage between Activity and Fragment. Both of them can be used to show the UI. To use a fragment, you need the Activity as its host, because Fragment must always be embedded in the Activity.
From the documentation:
A Fragment represents a behavior or a portion of user interface in an
Activity. You can combine multiple fragments in a single activity to
build a multi-pane UI and reuse a fragment in multiple activities. You
can think of a fragment as a modular section of an activity, which has
its own lifecycle, receives its own input events, and which you can
add or remove while the activity is running (sort of like a "sub
activity" that you can reuse in different activities).
A fragment must always be embedded in an activity and the fragment's
lifecycle is directly affected by the host activity's lifecycle.
You need to read Building a Dynamic UI with Fragments to mastering the Fragment. The steps to create a Fragment (Note, this not a strict rule):
Create the Activity as the host
Create the layout for Activity. Within, you need to create a FrameLayout view as the fragment holder.
Create the Fragment by extending Fragment class
Create the UI layout for the Fragment
Attach the Fragment to Activity by using FragmentTransaction
Now the create QR code part. You need to determine what information need to be shown in your QR code. Don't give all information in the QR code, because you mustn't expose all your user data to the world. If you have more than 1 string of information, you can use ";" or anything else to join the text info.
To build the QR code image, first, you need to include the ZXing library by using the following line in your app build.gradle (use the latest version):
compile 'com.google.zxing:core:3.3.0'
Then create the QR code bitmap using the following code:
private Bitmap textToImage(String text, int width, int height) throws WriterException, NullPointerException {
BitMatrix bitMatrix;
try {
bitMatrix = new MultiFormatWriter().encode(text, BarcodeFormat.DATA_MATRIX.QR_CODE,
width, height, null);
} catch (IllegalArgumentException Illegalargumentexception) {
return null;
}
int bitMatrixWidth = bitMatrix.getWidth();
int bitMatrixHeight = bitMatrix.getHeight();
int[] pixels = new int[bitMatrixWidth * bitMatrixHeight];
int colorWhite = 0xFFFFFFFF;
int colorBlack = 0xFF000000;
for (int y = 0; y < bitMatrixHeight; y++) {
int offset = y * bitMatrixWidth;
for (int x = 0; x < bitMatrixWidth; x++) {
pixels[offset + x] = bitMatrix.get(x, y) ? colorBlack : colorWhite;
}
}
Bitmap bitmap = Bitmap.createBitmap(bitMatrixWidth, bitMatrixHeight, Bitmap.Config.ARGB_4444);
bitmap.setPixels(pixels, 0, width, 0, 0, bitMatrixWidth, bitMatrixHeight);
return bitmap;
}
Then you can use it to set the generated image to your ImageView in your Fragment with something like this:
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.your_fragment_layout, container, false);
ImageView imvQrCode = (ImageView) view.findViewById(R.id.your_image_view);
Bitmap bitmap = textToImage("your_text_info", 500, 500);
imageView.setImageBitmap(bitmap);
return view;
}
You can find here how to create and use Fragments. But for generating QR Code I found one which is very tiny and smart library QRGen
Sample Code:
Bitmap myBitmap = QRCode.from("www.example.org").bitmap();
ImageView myImage = (ImageView) findViewById(R.id.imageView);
myImage.setImageBitmap(myBitmap);
try {
Bitmap bitmap= encodeAsBitmap("Muhammad Qasim Android Developer", BarcodeFormat.QR_CODE, Width, Height);
if (bitmap!= null) {
img.setImageBitmap(bitmap);
}
} catch (WriterException e) {
Log.e(""+e,"Exception");
}
After I take a picture with the Camera API, this picture displays on the screen/this activity. I want to send this picture that covers the whole screen to another activity called PictureEditor. There I will add functionality that can edit the picture.
// Code in MainActivity
mCamera.takePicture(null, null, mPicture);
Intent i = new Intent(getApplicationContext(), PictureEditor.class);
Bitmap b = getBitmapFromView(mPreview);
ByteArrayOutputStream bs = new ByteArrayOutputStream();
b.compress(Bitmap.CompressFormat.PNG, 50, bs);
i.putExtra("byteArray", bs.toByteArray());
startActivity(i);
In PictureEditor I have this code in OnCreate.
// Code in PictureEditor
if(getIntent().hasExtra("byteArray")) {
ImageView previewThumbnail = new ImageView(this);
Bitmap b = BitmapFactory.decodeByteArray(
getIntent().getByteArrayExtra("byteArray"),0,getIntent().getByteArrayExtra("byteArray").length);
previewThumbnail.setImageBitmap(b);
}
What can I do to retrive this picture in PictureEditor, and that this picture is the only thing that is visible on the screen in this activity? (Decode the bitmap and display it as an image on the screen)
Thanks for all kind of help!
Instead of startActivity call startActivityForResult and get the image from the bundle in onActivityResult call back method in the same activity and pass the image to the new Activity.
// Code in PictureEditor
if(getIntent().hasExtra("byteArray")) {
ImageView previewThumbnail = new ImageView(this);
Bitmap b =(Bitmap) getIntent().getParcelableExtra("byteArray");
previewThumbnail.setImageBitmap(b);
}
But if you send information between activitys. The size of this information cant exceed 1 MB. You have to compress your bitmap.