In my app I have a fragment which opens the device camera and allows the users to take photos and store them in a directory inside the gallery. This is the method that I use to create the dir and save the taken image:
private void saveImage(Bitmap finalBitmap, String image_name) {
final String appDirectoryName = "/Feel/";
String root = Environment.getExternalStoragePublicDirectory(
Environment.DIRECTORY_PICTURES).toString() + appDirectoryName;
File myDir = new File(root);
myDir.mkdirs();
String fname = "Image-" + image_name + ".jpg";
File file = new File(myDir, fname);
if (file.exists()) file.delete();
Log.i("LOAD", root + fname);
try {
FileOutputStream out = new FileOutputStream(file);
finalBitmap.compress(Bitmap.CompressFormat.JPEG, 90, out);
out.flush();
out.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
Everything works fine except finalBitmap.compress(Bitmap.CompressFormat.JPEG, 90, out);. When it comes to this line it skips the process... The directory is not created too... What is causing this problem?
This is my CameraFragment, where I retrieve the photo that was shot:
final Button btnShoot = viewCamera.findViewById(R.id.btnShoot);
imgUltimaFoto.setVisibility(View.INVISIBLE);
btnShoot.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
cmrView.addCameraListener(new CameraListener() {
#Override
public void onPictureTaken(final byte[] picture) {
super.onPictureTaken(picture);
CameraUtils.decodeBitmap(picture, new CameraUtils.BitmapCallback() {
#Override
public void onBitmapReady(Bitmap bitmap) {
imgUltimaFoto.setImageBitmap(bitmap);
imgUltimaFoto.setVisibility(View.VISIBLE);
saveImage(bitmap,"imagem1");
}
});
}
});
cmrView.capturePicture();
}
});
Related
I have an Image in web server and load it to Image View using Picasso perfectly then save it to a folder in internal storage memory every thing is OK but the problem is the saved image size is 0 byte
here is my code
File newDir=new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS),"km");
if (!newDir.exists()) {
if (!newDir.mkdirs()) {
Toast.makeText(this, "can not create directory", Toast.LENGTH_SHORT).show();
}
}
Picasso.with(this).load("http://192.168.1.101/cima/1.jpg").into(img);
File file = new File(new File("/storage/sdcard0/Download/km/"), "1.jpg");
img.buildDrawingCache();
Bitmap bmap = img.getDrawingCache();
if (file.exists()) {
file.delete();
}
try {
FileOutputStream out = new FileOutputStream(file);
bmap.compress(Bitmap.CompressFormat.JPEG, 100, out);
out.flush();
out.close();
} catch (Exception e) {
e.printStackTrace();
}
any help for this issue ??
Try to below code
Picasso.with(getActivity())
.load(url)
.into(new Target() {
#Override
public void onBitmapLoaded(Bitmap bitmap, Picasso.LoadedFrom from) {
try {
String root = Environment.getExternalStorageDirectory().toString();
File myDir = new File(root + "/yourDirectory");
if (!myDir.exists()) {
myDir.mkdirs();
}
String name = new Date().toString() + ".jpg";
myDir = new File(myDir, name);
FileOutputStream out = new FileOutputStream(myDir);
bitmap.compress(Bitmap.CompressFormat.JPEG, 90, out);
out.flush();
out.close();
} catch(Exception e){
// some action
}
}
#Override
public void onBitmapFailed(Drawable errorDrawable) {
}
#Override
public void onPrepareLoad(Drawable placeHolderDrawable) {
}
}
);
Now I have app which save and read some text into .txt file by button. How can I make that app save file after app closed and reading file when app opened automatically, without any click on buttons?
public class mAcitivity extends AppCompatActivity {
private Button btn_read, btn_save;
private TextView textView;
private String txt = "";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
btn_save.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
saveFile();
}
});
btn_read.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
readFile();
textView.setText(txt);
}
});
}
public String readFile() {
String root = Environment.getExternalStorageDirectory().toString();
File myDir = new File(root + "/TEST");
myDir.mkdirs();
File file = new File(myDir, "file.txt");
try {
FileInputStream fis = new FileInputStream(file);
int size = fis.available();
byte[] buffer = new byte[size];
fis.read(buffer);
fis.close();
txt = new String(buffer);
} catch (Exception e) {
e.printStackTrace();
Toast.makeText(mActivity.this, "Error reading file", Toast.LENGTH_LONG).show();
}
return txt;
}
public void saveFile() {
String root = Environment.getExternalStorageDirectory().toString();
File myDir = new File(root + "/TEST");
myDir.mkdirs();
File file = new File(myDir, "file.txt");
if (file.exists()){ file.delete();}
try {
String sometxt = "Hello world";
FileOutputStream out = new FileOutputStream(file);
PrintWriter pw = new PrintWriter(out);
pw.println(sometxt);
pw.flush();
pw.close();
out.flush();
out.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
You can use your MainActivity lifecycle callbacks to begin your I/O operations directly, or start BoundService which will operate them.
You can achieve this by putting your saveFile() method inside stop() lifecycle method, and putting your readFile() method inside start() lifecycle method. Activity will automatically call start() method once the application starts and it will call stop() method once the applicqtion closes/terminates.
I am implementing a button which lets you take a screenshot, but I want to save it on the Android Internal Storage not in the External Storage (SD Card).
I tried this:
private String saveToInternalStorage(Bitmap bitmapImage){
ContextWrapper cw = new ContextWrapper(getApplicationContext());
// path to /data/data/yourapp/app_data/imageDir
File directory = cw.getDir("imageDir", Context.MODE_PRIVATE);
// Create imageDir
File mypath=new File(directory,"profile.jpg");
FileOutputStream fos = null;
try {
fos = new FileOutputStream(mypath);
// Use the compress method on the BitMap object to write image to the OutputStream
bitmapImage.compress(Bitmap.CompressFormat.PNG, 100, fos);
} catch (Exception e) {
e.printStackTrace();
} finally {
fos.close();
}
return directory.getAbsolutePath();
}
I've started this method with an OnClick method of a button:
private void takeScreenshot(View v) {
v = getWindow().getDecorView().getRootView();
v.setDrawingCacheEnabled(true);
Bitmap bitmap = Bitmap.createBitmap(v.getDrawingCache());
v.setDrawingCacheEnabled(false);
saveToInternalStorage(bitmap)
}
But this didn't work. Instead, when I click the button, an error message appears on my cell phone: "Application has stopped".
Hope you can help me.
I think you need to use openFileOutput to get a FileOutputStream, try following the example in the doc https://developer.android.com/training/basics/data-storage/files.html
What's the error in the logcat?
/**
* This function captures any Android views to a bitmap shapshot
* and save it to a file path
* and optionally open it with android pciture viewer
*/
public void CaptureView(View view, String filePath, boolean bOpen) {
view.setDrawingCacheEnabled(true);
Bitmap b = view.getDrawingCache();
try {
b.compress(CompressFormat.JPEG, 95, new FileOutputStream(filePath));
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
if (bOpen) {
Intent intent = new Intent();
intent.setAction(Intent.ACTION_VIEW);
intent.setDataAndType(Uri.parse("file://" + filePath), "image/*");
startActivity(intent);
}
}
Usage:
File sdcard = Environment.getExternalStorageDirectory();
String path = sdcard + "/demo.jpg";
CaptureView(someViewInstace, path, false);
You can use Context.getFilesDir() method to get the path to the internal storage:
String path = yourActivity.getFilesDir() + "/" + name);
Add permission in manifest file
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
add this line manifest file application tag
android:requestLegacyExternalStorage="true"
In activity
public class MainActivity extends AppCompatActivity {
private static final int REQUEST_EXTERNAL_STORAGE = 1;
private static String[] PERMISSIONS_STORAGE = {
Manifest.permission.WRITE_EXTERNAL_STORAGE
};
Button button;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
button = findViewById(R.id.button);
button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
int permission = ActivityCompat.checkSelfPermission(MainActivity.this,
Manifest.permission.WRITE_EXTERNAL_STORAGE);
if (permission != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(
MainActivity.this,
PERMISSIONS_STORAGE,
REQUEST_EXTERNAL_STORAGE);
} else {
takeScreenshot();
}
}
});
}
private void takeScreenshot() {
Date now = new Date();
android.text.format.DateFormat.format("yyyy-MM-dd_hh:mm:ss", now);
try {
// image naming and path to include sd card appending name you choose for file
String mPath = Environment.getExternalStorageDirectory().toString() + "/" + now + ".jpg";
// create bitmap screen capture
View v1 = getWindow().getDecorView().getRootView();
v1.setDrawingCacheEnabled(true);
Bitmap bitmap = Bitmap.createBitmap(v1.getDrawingCache());
v1.setDrawingCacheEnabled(false);
File imageFile = new File(mPath);
FileOutputStream outputStream = new FileOutputStream(imageFile);
int quality = 100;
bitmap.compress(Bitmap.CompressFormat.JPEG, quality, outputStream);
outputStream.flush();
outputStream.close();
Toast.makeText(MainActivity.this, "Successfully saved", Toast.LENGTH_SHORT).show();
//**if you want to open this screenshot
openScreenshot(imageFile);
} catch (Throwable e) {
e.printStackTrace();
}
}
private void openScreenshot(File imageFile) {
Intent intent = new Intent();
intent.setAction(Intent.ACTION_VIEW);
Uri uri = Uri.fromFile(imageFile);
intent.setDataAndType(uri, "image/*");
startActivity(intent);
}
}
I've been working out how to take a screenshot programmatically in android, however when it screenshots I get a toolbar and black screen captured instead of what is actually on the screen.
I've also tried to screenshot a particular TextView within the custom InfoWindow layout I created for the google map. But that creates a null pointer exception on the second line below.
TextView v1 = (TextView)findViewById(R.id.tv_code);
v1.setDrawingCacheEnabled(true);
Is there anyway to either actually screenshot what is on the screen without installing android screenshot library or to screenshot a TextView within a custom InfoWindow layout
This is my screenshot method:
/**
* Method to take a screenshot programmatically
*/
private void takeScreenshot(){
try {
//TextView I could screenshot instead of the whole screen:
//TextView v1 = (TextView)findViewById(R.id.tv_code);
View v1 = getWindow().getDecorView().getRootView();
v1.setDrawingCacheEnabled(true);
Bitmap bitmap = Bitmap.createBitmap(v1.getDrawingCache());
v1.setDrawingCacheEnabled(false);
ByteArrayOutputStream bytes = new ByteArrayOutputStream();
bitmap.compress(Bitmap.CompressFormat.JPEG, 40, bytes);
File f = new File(Environment.getExternalStorageDirectory()
+ File.separator + "test.jpg");
FileOutputStream fo = new FileOutputStream(f);
fo.write(bytes.toByteArray());
fo.flush();
fo.close();
MediaStore.Images.Media.insertImage(getContentResolver(), f.getAbsolutePath(), f.getName(), f.getName());
Log.d("debug", "Screenshot saved to gallery");
Toast.makeText(HuntActivity.this,"Code Saved!",Toast.LENGTH_LONG).show();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
EDIT: I have changed the method to the one provided from the source
How can i take/merge screen shot of Google map v2 and layout of xml both programmatically?
However it does not screenshot anything.
public void captureMapScreen() {
GoogleMap.SnapshotReadyCallback callback = new GoogleMap.SnapshotReadyCallback() {
#Override
public void onSnapshotReady(Bitmap snapshot) {
try {
View mView = getWindow().getDecorView().getRootView();
mView.setDrawingCacheEnabled(true);
Bitmap backBitmap = mView.getDrawingCache();
Bitmap bmOverlay = Bitmap.createBitmap(
backBitmap.getWidth(), backBitmap.getHeight(),
backBitmap.getConfig());
Canvas canvas = new Canvas(bmOverlay);
canvas.drawBitmap(backBitmap, 0, 0, null);
canvas.drawBitmap(snapshot, new Matrix(), null);
FileOutputStream out = new FileOutputStream(
Environment.getExternalStorageDirectory()
+ "/"
+ System.currentTimeMillis() + ".jpg");
bmOverlay.compress(Bitmap.CompressFormat.JPEG, 90, out);
} catch (Exception e) {
e.printStackTrace();
}
}
};
mMap.snapshot(callback);
}
Use this code
private void takeScreenshot() {
AsyncTask<Void, Void, Void> asyc = new AsyncTask<Void, Void, Void>() {
#Override
protected void onPreExecute() {
super.onPreExecute();
objUsefullData.showProgress("Please wait", "");
}
#Override
protected Void doInBackground(Void... params) {
try {
// create bitmap screen capture
View v1 = getWindow().getDecorView().getRootView();
v1.setDrawingCacheEnabled(true);
bitmapscreen_shot = Bitmap.createBitmap(v1
.getDrawingCache());
v1.setDrawingCacheEnabled(false);
String state = Environment.getExternalStorageState();
File folder = null;
if (state.contains(Environment.MEDIA_MOUNTED)) {
folder = new File(
Environment.getExternalStorageDirectory()
+ "/piccapella");
} else {
folder = new File(
Environment.getExternalStorageDirectory()
+ "/piccapella");
}
boolean success = true;
if (!folder.exists()) {
success = folder.mkdirs();
}
if (success) {
// Create a media file name
String timeStamp = new SimpleDateFormat(
"yyyyMMdd_HHmmss", Locale.getDefault())
.format(new java.util.Date());
imageFile = new File(folder.getAbsolutePath()
+ File.separator + "IMG_" + timeStamp + ".jpg");
/*
* Toast.makeText(AddTextActivity.this,
* "saved Image path" + "" + imageFile,
* Toast.LENGTH_SHORT) .show();
*/
imageFile.createNewFile();
} else {
/*
* Toast.makeText(AddTextActivity.this,
* "Image Not saved", Toast.LENGTH_SHORT).show();
*/
}
ByteArrayOutputStream ostream = new ByteArrayOutputStream();
// save image into gallery
bitmapscreen_shot.compress(CompressFormat.JPEG, 100,
ostream);
FileOutputStream fout = new FileOutputStream(imageFile);
fout.write(ostream.toByteArray());
fout.close();
Log.e("image_screen_shot", "" + imageFile);
} catch (Throwable e) {
// Several error may come out with file handling or OOM
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(Void result) {
// TODO Auto-generated method stub
super.onPostExecute(result);
objUsefullData.dismissProgress();
}
};
asyc.execute();
}
Hope this will help you
I have figured it out !
/**
* Method to take a screenshot programmatically
*/
private void takeScreenshot(){
GoogleMap.SnapshotReadyCallback callback = new GoogleMap.SnapshotReadyCallback() {
#Override
public void onSnapshotReady(Bitmap bitmap) {
Bitmap b = bitmap;
String timeStamp = new SimpleDateFormat(
"yyyyMMdd_HHmmss", Locale.getDefault())
.format(new java.util.Date());
String filepath = timeStamp + ".jpg";
try{
OutputStream fout = null;
fout = openFileOutput(filepath,MODE_WORLD_READABLE);
bitmap.compress(Bitmap.CompressFormat.JPEG, 90, fout);
fout.flush();
fout.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
saveImage(filepath);
}
};
mMap.snapshot(callback);
}
/**
* Method to save the screenshot image
* #param filePath the file path
*/
public void saveImage(String filePath)
{
File file = this.getFileStreamPath(filePath);
if(!filePath.equals(""))
{
final ContentValues values = new ContentValues(2);
values.put(MediaStore.Images.Media.MIME_TYPE, "image/jpeg");
values.put(MediaStore.Images.Media.DATA, file.getAbsolutePath());
final Uri contentUriFile = getContentResolver().insert(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values);
Toast.makeText(HuntActivity.this,"Code Saved to files!",Toast.LENGTH_LONG).show();
}
else
{
System.out.println("ERROR");
}
}
I have adapted the code from this link so it doesn't share and instead just saves the image.
Capture screen shot of GoogleMap Android API V2
Thanks for everyones help
Please try with the code below:
private void takeScreenshot(){
try {
//TextView I could screenshot instead of the whole screen:
//TextView v1 = (TextView)findViewById(R.id.tv_code);
Bitmap bitmap = null;
Bitmap bitmap1 = null;
View v1 = getWindow().getDecorView().getRootView();
v1.setDrawingCacheEnabled(true);
bitmap = Bitmap.createBitmap(v1.getDrawingCache());
try {
if (bitmap != null)
bitmap1 = Bitmap.createBitmap(bitmap, 0, 0,
v1.getWidth(), v1.getHeight());
} catch (OutOfMemoryError e) {
e.printStackTrace();
}
v1.setDrawingCacheEnabled(false);
ByteArrayOutputStream bytes = new ByteArrayOutputStream();
bitmap1.compress(Bitmap.CompressFormat.JPEG, 40, bytes);
File f = new File(Environment.getExternalStorageDirectory()
+ File.separator + "test.jpg");
FileOutputStream fo = new FileOutputStream(f);
fo.write(bytes.toByteArray());
fo.flush();
fo.close();
MediaStore.Images.Media.insertImage(getContentResolver(), f.getAbsolutePath(), f.getName(), f.getName());
Log.d("debug", "Screenshot saved to gallery");
Toast.makeText(HuntActivity.this,"Code Saved!",Toast.LENGTH_LONG).show();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
I faced this issue. After v1.setDrawingCacheEnabled(true); I added,
v1.buildDrawingCache();
And put some delay to call the takeScreenshot(); method.
It is fixed.
I'm creating a android app that has the following purpose:
Save the canvas as image on SD card
Always keep the first picture even after I clean (with ClearPaint button)
Paint a new picture will keep the previous image again
Code:
Button Colorpaint = (Button) findViewById(R.id.color);
Colorpaint.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
int _color = R.color.red;
new PickerDialog(v.getContext(),new OnColorChangedListener() {
public void colorChanged(int color) {
mPaint.setColor(color);
Log.i("TAG", "mpaint one" +mPaint);
}
}, mPaint.getColor(), _color).show();
Log.i("TAG", "mpaint two" +mPaint);
}
});
ClearPaint = (Button) findViewById(R.id.ClearPaint);
ClearPaint.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
mBitmap.eraseColor(Color.TRANSPARENT);
mPath.reset();
mView.invalidate();
}
});
btn_shoot = (Button)findViewById(R.id.btn_shoot);
btn_shoot.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
View view = findViewById(R.id.item);
view.setDrawingCacheEnabled(true);
Bitmap bitmap = view.getDrawingCache();
BitmapDrawable bitmapDrawable = new BitmapDrawable(bitmap);
if (Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState())) {
//we check if external storage is available, otherwise display an error message to the user
File sdCard = Environment.getExternalStorageDirectory();
File directory = new File (sdCard.getAbsolutePath() + "/Basketball_Coach_Board");
directory.mkdirs();
String filename = "tactics" + i + ".jpg";
File yourFile = new File(directory, filename);
while (yourFile.exists()) {
i++;
filename = "tactics" + i + ".jpg";
yourFile = new File(directory, filename);
}
if (!yourFile.exists()) {
if (directory.canWrite())
{
try {
FileOutputStream out = new FileOutputStream(yourFile, true);
bitmap.compress(Bitmap.CompressFormat.PNG, 90, out);
out.flush();
out.close();
Toast.makeText(MainActivity.this, "Tactics saved at /sdcard/Basketball_Coach_Board/tactics" + i + ".jpg", Toast.LENGTH_SHORT).show();
i++;
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
else
{
Toast.makeText(MainActivity.this, "SD Card not available!", Toast.LENGTH_SHORT).show();
}
}
});
I guess this is because after successfully taking the picture you don't reset the drawing cache to false with: view.setDrawingCacheEnabled(false);