I have created a view MyToggleButton
that extends ToogleButton
. I overwrite the Togglebutton's onDraw
method to draw a line on the button and to rotate it's text.
Here is MyToggleButton
:
package com.example.gl.myapplication;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.text.TextPaint;
import android.widget.ToggleButton;
public class MyToggleButton extends ToggleButton {
public float textRotation=0;
public MyToggleButton(Context context, float rotationValue) {
super(context);
textRotation=rotationValue;
}
@Override
protected void onDraw(Canvas canvas){
TextPaint textPaint = getPaint();
textPaint.setColor(getCurrentTextColor());
textPaint.drawableState = getDrawableState();
canvas.save();
//paint
Paint paint = new Paint();
paint.setColor(Color.BLACK);
paint.setStrokeWidth(7);
paint.setStrokeCap(Paint.Cap.ROUND);
canvas.drawLine(canvas.getWidth() / 2, canvas.getHeight() / 2, (float) (canvas.getHeight() / 2 + 400), (canvas.getHeight() / 2), paint);
canvas.rotate(textRotation, canvas.getWidth() / 2, canvas.getHeight() / 2);
getLayout().draw(canvas);
canvas.restore();
}
}
After that I want to get a screenshot of and view it and for that I use the takeScreenshot()
method that is called by pressing the 3rd button on screen. The screenshot code is based on How to programmatically take a screenshot in Android?. The same approach is followed in other posts on stackoverflow, and in various sites and tutorials I found around.
Here is the MainActivity
that I use:
package com.example.gl.myapplication;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.PorterDuff;
import android.graphics.PorterDuffXfermode;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.AbsListView;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.RelativeLayout;
import android.widget.Toast;
import java.io.File;
import java.io.FileOutputStream;
import java.util.Date;
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//add 3 buttons
addButtons();
}
private void addButtons(){
LinearLayout linear1= (LinearLayout) findViewById(R.id.vert1);
//MyToggleButton with rotated text
MyToggleButton btn1 = new MyToggleButton(this,0);
btn1.setLayoutParams(new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT,
LinearLayout.LayoutParams.WRAP_CONTENT));
btn1.setTextOff("Button 1 not rotated");
btn1.setTextOn("Button 1 not rotated");
btn1.setText("Button 1 not rotated");
linear1.addView(btn1);
//MyToggleButton with normal text
MyToggleButton btn2 = new MyToggleButton(this,50);
btn2.setLayoutParams(new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT,
LinearLayout.LayoutParams.WRAP_CONTENT));
btn2.setTextOff("Button 2 rotated");
btn2.setTextOn("Button 2 rotated");
btn2.setText("Button 2 rotated");
linear1.addView(btn2);
//button to create screenshot
Button btn3 = new Button(this);
btn3.setText("Create bitmap");
btn3.setOnClickListener(new Button.OnClickListener() {
public void onClick(View v) {
takeScreenshot();
}
});
linear1.addView(btn3);
}
//Screenshotcreator
private void takeScreenshot() {
try {
View v1 = getWindow().getDecorView().getRootView();
// create bitmap screen capture
v1.setDrawingCacheEnabled(true);
Bitmap bitmap = Bitmap.createBitmap(v1.getDrawingCache());
v1.setDrawingCacheEnabled(false);
ImageView imageView1 =(ImageView) findViewById(R.id.imageView1);
imageView1.setImageBitmap(bitmap);
} catch (Throwable e) {
e.printStackTrace();
}
}
}
Here is the layout of MainActivity
:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.example.gl.myapplication.MainActivity"
android:id="@+id/relative1">
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/vert1">
<ImageView
android:layout_width="wrap_content"
android:layout_height="250dp"
android:id="@+id/imageView1" />
</LinearLayout>
</RelativeLayout>
The problem is that although everything looks ok on the screen, the screenshot's bitmap lacks the drawn line and the rotated text.
What could be the reason for that strange result in the bitmap?
Notice that that the devices back-home-recents buttons are missing from the screenshot, as also the status bar information (time etc). I doubt that this has to do something with my issue. Those elements do not belong in my app so it is expected for them to not appear in the view I get with get with v1 = getWindow().getDecorView().getRootView();
But the canvas on which I draw the rotated text and the line do belong to that view.
My question is: Why does the drawn line and the rotated text do not appear on the screenshot, and how can I modify my code to get a screenshot with them on too?
I don't want to do something that needs a rooted device and also I cannot use MediaProjection API because this was added in API 21 but I want my app to run on android 4.4 (API 19) too. Finally, I am aware of the existence of external libraries such as Android Screenshot Library or this: https://android-arsenal.com/details/1/2793 , but I would rather not use any external library.
P.S. maybe this is related:Surfaceview screenshot with line/ellipse drawn over it