Email Intent sends text file rather than image - java

This the code I am using to take picture, display it, then send it in an email:
private void takePicture() {
Intent intent = new Intent("android.media.action.IMAGE_CAPTURE");
File photo = new File(Environment.getExternalStorageDirectory(),
getIntent().getStringExtra("counter"));
intent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(photo));
imageUri = Uri.fromFile(photo);
startActivityForResult(intent, 0);
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
switch (requestCode) {
case 0:
if (resultCode == Activity.RESULT_OK) {
Uri selectedImage = imageUri;
getContentResolver().notifyChange(selectedImage, null);
ContentResolver cr = getContentResolver();
try {
bitmap = android.provider.MediaStore.Images.Media
.getBitmap(cr, selectedImage);
savePicture(getIntent().getStringExtra("counter"), bitmap,
getApplicationContext());
setImage();
Toast.makeText(this, selectedImage.toString(), Toast.LENGTH_LONG).show();
} catch (Exception e) {
}
}
}
}
How I send the email:
final Intent emailIntent = new Intent(
android.content.Intent.ACTION_SEND);
String fileName = null;
try {
fileName = URLEncoder.encode(getIntent().getStringExtra("counter"), "UTF-8");
} catch (UnsupportedEncodingException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
String path = Environment.getExternalStorageDirectory()+"/"+fileName.trim().toString();
Uri uri = Uri.parse("file://"+path);
emailIntent.setType("image/png");
emailIntent.putExtra(android.content.Intent.EXTRA_STREAM, uri);
/* Send it off to the Activity-Chooser */
startActivity(Intent
.createChooser(emailIntent, "Send Email..."));
Notice, my file name should be getIntent().getStringExtra("counter");
When I do this, my email sends a text file rather than an image file. I have no clue why it does this...

I suspect this has happened to more than one person, but the problem was this:
I had to add +".jpg" to the end of the filename, and now it works. This may have been a simple solution but it surely was a distressful problem!
Hope this post still helps those who encounter this issue in the future.

Related

Android VIEW intent with content Uri

I am creating a App, which should save reference documents, saved on the device.
I am receiving the content URI for these documents in the following way:
private void selectDocument() {
Intent chooseFile;
chooseFile = new Intent(Intent.ACTION_GET_CONTENT);
chooseFile.addCategory(Intent.CATEGORY_OPENABLE);
chooseFile.setType("*/*");
if (chooseFile.resolveActivity(getPackageManager()) != null)
startActivityForResult(chooseFile, ACTIVITY_CHOOSE_FILE);
}
#Override
protected void onActivityResult(int requestCode, int resultCode, #Nullable Intent data) {
if (resultCode != RESULT_OK) return;
if (requestCode == ACTIVITY_CHOOSE_FILE) {
try {
binding.txtLink.setText(URLDecoder.decode(data.getDataString(),"UTF-8"));
binding.btnLink.setTag(false);
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
} else {
super.onActivityResult(requestCode, resultCode, data);
}
}
after displaying the url to the user, he should be able to open the document.
And i am not really sure how to do that, since I only get the contentURI.
What i am currently trying is this:
private void openDocument() {
String file = binding.txtLink.getText().toString();
if (file.isEmpty()) {
return;
}
Intent intent;
String extension = file.substring(file.lastIndexOf(".") + 1);
String mimeType = MimeTypeMap.getSingleton().getMimeTypeFromExtension(extension);
intent = new Intent(Intent.ACTION_VIEW);
intent.setData(Uri.parse(file));
if (intent.resolveActivity(getPackageManager()) != null) {
startActivity(intent);
} else {
Snackbar.make(binding.root, "Keine Anwendung zum öffnen der Datei installiert", Snackbar.LENGTH_LONG).show();
}
}
This already opens the correct App, but they can't find the files.
What would i need to do, to enable this behavior?
Or do i have to copy the files to my app directory and open them from there?

Take picture from linear layout and save to gallery

How can I take picture from LinearLayout and save it to gallery? For example my LinearLayout name is ll I want to take picture from ll and save it to the gallery.
I think you mean to take photo from your mobile desktop programmatically ?if so use intent to take photo.you can search the net for intent to take photo.
you can use this block of code.
private static final int TAKE_PICTURE = 1;
private Uri imageUri;
public void takePhoto(View view) {
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
File photo = new File(Environment.getExternalStorageDirectory(), "Pic.jpg");
intent.putExtra(MediaStore.EXTRA_OUTPUT,
Uri.fromFile(photo));
imageUri = Uri.fromFile(photo);
startActivityForResult(intent, TAKE_PICTURE);
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
switch (requestCode) {
case TAKE_PICTURE:
if (resultCode == Activity.RESULT_OK) {
Uri selectedImage = imageUri;
getContentResolver().notifyChange(selectedImage, null);
ImageView imageView = (ImageView) findViewById(R.id.ImageView);
ContentResolver cr = getContentResolver();
Bitmap bitmap;
try {
bitmap = android.provider.MediaStore.Images.Media
.getBitmap(cr, selectedImage);
imageView.setImageBitmap(bitmap);
Toast.makeText(this, selectedImage.toString(),
Toast.LENGTH_LONG).show();
} catch (Exception e) {
Toast.makeText(this, "Failed to load", Toast.LENGTH_SHORT)
.show();
Log.e("Camera", e.toString());
}
}
}
}

java.net.MalformedURLException trying to retrieve a photo saved on my Android device

I am trying to add in my App a function to use the camera to store photos in my device.
At the beginning i use the camera like this:
mButtonCamera.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
count++;
String file = dir+prova+".jpg";
File newFile = new File(file);
try {
newFile.createNewFile();
}catch (IOException e){}
Uri outputFileUri = Uri.fromFile(newFile);
Intent cameraIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
cameraIntent.putExtra(MediaStore.EXTRA_OUTPUT,outputFileUri);
Log.v("CameraDemo", "Pic savedNO");
startActivityForResult(cameraIntent, TAKE_PHOTO_CODE);
}
});
And then for the OnActivityResult:
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == TAKE_PHOTO_CODE && resultCode == RESULT_OK) {
Log.v("CameraDemo", "Pic saved");
Log.v("Salva Foto", dir+prova+".jpg");
myDBHandler.addPhoto(prova,dir+prova+".jpg");
}
}
Until here evrything is ok but when I try to retrieve the photo using this:
InputStream URLcontent = null;
try {
URLcontent = (InputStream) new URL(fotoSI).getContent();
} catch (IOException e) {
e.printStackTrace();
}
Drawable image = Drawable.createFromStream(URLcontent, fotoSI);
mImageCamera.setImageDrawable(image);
It doesn´t return any photo that is what the Log says me:
java.net.MalformedURLException: Protocol not found: /storage/emulated/0/Pictures/
I am trying everything but without results.

MediaStore.EXTRA_OUTPUT renders data null, other way to save photos?

Google offers this versatile code for taking photos via an intent:
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
// create Intent to take a picture and return control to the calling application
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
fileUri = getOutputMediaFileUri(MEDIA_TYPE_IMAGE); // create a file to save the image
intent.putExtra(MediaStore.EXTRA_OUTPUT, fileUri); // set the image file name
// start the image capture Intent
startActivityForResult(intent, CAPTURE_IMAGE_ACTIVITY_REQUEST_CODE);
}
The problem is that if you're like me and you want to pass the photos as extras, using EXTRA_OUTPUT seemingly runs off with the photo data and makes subsequent actions think the intent data is null.
It appears this is a big bug with Android.
I'm trying to take a photo then display it as a thumbnail in a new view. I'd like to have it saved as a full sized image in the user's gallery. Does anyone know a way to specify the image location without using EXTRA_OUTPUT?
Here's what I have currently:
public void takePhoto(View view) {
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
fileUri = getOutputMediaFileUri(MEDIA_TYPE_IMAGE);
// takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, fileUri);
startActivityForResult(takePictureIntent, CAMERA_REQUEST_CODE);
}
/** Create a file Uri for saving an image or video */
private static Uri getOutputMediaFileUri(int type){
return Uri.fromFile(getOutputMediaFile(type));
}
/** Create a File for saving an image or video */
#SuppressLint("SimpleDateFormat")
private static File getOutputMediaFile(int type){
File mediaStorageDir = new File(Environment.getExternalStoragePublicDirectory(
Environment.DIRECTORY_PICTURES), "JoshuaTree");
if (! mediaStorageDir.exists()){
if (! mediaStorageDir.mkdirs()){
Log.d("JoshuaTree", "failed to create directory");
return null;
}
}
// Create a media file name
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
File mediaFile;
if (type == MEDIA_TYPE_IMAGE){
mediaFile = new File(mediaStorageDir.getPath() + File.separator +
"IMG_"+ timeStamp + ".jpg");
} else {
return null;
}
return mediaFile;
}
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == CAMERA_REQUEST_CODE) {
if (resultCode == RESULT_OK) {
handleSmallCameraPhoto(data);
}
}
}
private void handleSmallCameraPhoto(Intent intent) {
Bundle extras = intent.getExtras();
mImageBitmap = (Bitmap) extras.get("data");
Intent displayIntent = new Intent(this, DisplayPhotoActivity.class);
displayIntent.putExtra("BitmapImage", mImageBitmap);
startActivity(displayIntent);
}
}
If you specified MediaStore.EXTRA_OUTPUT, the image taken will be written to that path, and no data will given to onActivityResult. You can read the image from what you specified.
See another solved same question here: Android Camera : data intent returns null
Basically, there are two ways to retrieve the image from Camera, if you use to send a captured image through intent extras you cannot retrieve it on ActivityResult on intent.getData() ' because it saves the image data through extras.
So the idea is:
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
startActivityForResult(intent, CAPTURE_IMAGE_ACTIVITY_REQUEST_CODE);
And retrieving it on ActivityResults checking the retrieved intent:
#Override
public void onActivityResult(int requestCode, int resultCode, Intent intent) {
if (resultCode == RESULT_OK) {
if (requestCode == CAPTURE_IMAGE_ACTIVITY_REQUEST_CODE) {
if (intent.getData() != null) {
ParcelFileDescriptor parcelFileDescriptor = context.getContentResolver().openFileDescriptor(intent.getData(), "r"); 
FileDescriptor fileDescriptor = parcelFileDescriptor.getFileDescriptor();
Bitmap image = BitmapFactory.decodeFileDescriptor(fileDescriptor);
parcelFileDescriptor.close();
} else {
Bitmap imageRetrieved = (Bitmap) intent.getExtras().get("data");
}
}
}
}
Here is how you can achieve what you want:
public void onClick(View v)
{
switch(v.getId())
{
case R.id.iBCamera:
File image = new File(appFolderCheckandCreate(), "img" + getTimeStamp() + ".jpg");
Uri uriSavedImage = Uri.fromFile(image);
Intent i = new Intent(android.provider.MediaStore.ACTION_IMAGE_CAPTURE);
i.putExtra(MediaStore.EXTRA_OUTPUT, uriSavedImage);
i.putExtra("return-data", true);
startActivityForResult(i, CAMERA_RESULT);
break;
}
}
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data)
{
super.onActivityResult(requestCode, resultCode, data);
switch(requestCode)
{
case CAMERA_RESULT:
if(resultCode==RESULT_OK)
{
handleSmallCameraPhoto(uriSavedImage);
}
break;
}
}
private void handleSmallCameraPhoto(Uri uri)
{
Bitmap bmp=null;
try {
bmp = BitmapFactory.decodeStream(getContentResolver().openInputStream(uri));
}
catch (FileNotFoundException e)
{
e.printStackTrace();
}
Intent displayIntent = new Intent(this, DisplayPhotoActivity.class);
displayIntent.putExtra("BitmapImage", bmp);
startActivity(displayIntent);
}
private String appFolderCheckandCreate(){
String appFolderPath="";
File externalStorage = Environment.getExternalStorageDirectory();
if (externalStorage.canWrite())
{
appFolderPath = externalStorage.getAbsolutePath() + "/MyApp";
File dir = new File(appFolderPath);
if (!dir.exists())
{
dir.mkdirs();
}
}
else
{
showToast(" Storage media not found or is full ! ");
}
return appFolderPath;
}
private String getTimeStamp() {
final long timestamp = new Date().getTime();
final Calendar cal = Calendar.getInstance();
cal.setTimeInMillis(timestamp);
final String timeString = new SimpleDateFormat("HH_mm_ss_SSS").format(cal.getTime());
return timeString;
}
Edit:
Add these to Manifest:
Starting Api 19 and above READ_EXTERNAL_STORAGE should be declared explicitly
*<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />*
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
to you manifest.
Try this one android.provider.MediaStore.EXTRA_OUTPUT hope will solve your bug. The following code works for me:
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
fileUri = getOutputMediaFileUri(MEDIA_TYPE_IMAGE);
intent.putExtra(android.provider.MediaStore.EXTRA_OUTPUT, fileUri);
startActivityForResult(intent, CAPTURE_IMAGE_ACTIVITY_REQUEST_CODE);
I was facing same problem, every time getting null while retrieving data on other activity with getIntent().getData() then solved by writting complete android.provider.MediaStore.EXTRA_OUTPUT this solved my bug.

Using the camera intent to take a picture without an sdcard

I'm having trouble using the camera when there's no sdcard present.
When there is an sdcard, using the camera is trivial, e.g.
http://www.vogella.com/articles/AndroidCamera/article.html + a plethora of other examples.
However, I need to make my app available to devices which don't have SD cards, (e.g. the Sony Xperia series.) I've tried modifying the code such that I'm using the internal storage (I think):
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
File file = new File(getDir("myDirec", Context.MODE_WORLD_WRITEABLE), "tmp_photo_" + String.valueOf(System.currentTimeMillis()) + ".jpg");
file.createNewFile();
mImageCaptureUri = Uri.fromFile(file);
intent.putExtra(android.provider.MediaStore.EXTRA_OUTPUT, mImageCaptureUri);
intent.putExtra("return-data", true);
However, upon result:
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent intentReturn) {
if (resultCode != RESULT_OK)
return;
String path = mImageCaptureUri.getPath();
Bitmap bitmap = BitmapFactory.decodeFile(path);
...
bitmap is null.
Which leads me to believe that there's some permissions issue....maybe?
I've tried some of the other internal storage options, http://developer.android.com/guide/topics/data/data-storage.html#filesInternal e.g. getFilesDir() but the same result: null bitmap.
Has anyone had any success in using the camera without an sdcard?
Try this. It works..
private Uri imageUri;
public void onClick(View arg0) {
switch (arg0.getId()) {
case R.id.btnImageCapture:
Intent intent = new Intent("android.media.action.IMAGE_CAPTURE");
File dir = context.getDir("directory", Context.MODE_PRIVATE);
File photo = new File(dir, "Pic.jpg");
intent.putExtra(MediaStore.EXTRA_OUTPUT,
Uri.fromFile(photo));
imageUri = Uri.fromFile(photo);
startActivityForResult(intent, OPEN_CAMERA);
break;
}
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
switch (requestCode) {
case OPEN_CAMERA:
if (resultCode == Activity.RESULT_OK) {
Uri selectedImage = imageUri;
getContentResolver().notifyChange(selectedImage, null);
ImageView imageView = (ImageView) findViewById(R.id.ImageView);
ContentResolver cr = getContentResolver();
Bitmap bitmap;
try {
bitmap = android.provider.MediaStore.Images.Media
.getBitmap(cr, selectedImage);
imageView.setImageBitmap(bitmap);
Toast.makeText(this, selectedImage.toString(),
Toast.LENGTH_LONG).show();
} catch (Exception e) {
Toast.makeText(this, "Failed to load", Toast.LENGTH_SHORT)
.show();
}
}
}
}

Categories

Resources