Image File Saved on Android Device Not Opening - android

I need to display an image and some HTML associated with it in a WebView. I get the image as byte[]. I am creating a .PNG file using the following code.
private string CreatePNG(byte[] data)
{
string filePath = Android.OS.Environment.ExternalStorageDirectory.Path;
string fileName = System.Guid.NewGuid().ToString() + ".png";
File.WriteAllBytes(Path.Combine(filePath, fileName), data);
return Path.Combine(filePath, fileName);
}
Then I embed the .PNG file in my HTML using the following code.
html += #"<img src=""file://" + CreatePNG(page.DocumentImage) + "\"/><br><br>";
The image shows as blank in my app. The text shows properly. If I try to open the image directly on the phone after browsing from "File Manager", it still shows as blank. When I copy the image from the phone to my Mac, it opens up fine.
Can someone please advise what is going wrong here?

Related

Android webview - how to pass a large binray file to Javascript

I have a mobile app that wraps around the web-app, using webview.
The web-app has a button to open a large .zip file (e.g. 100 MB).
The user clicks a button, and selects a .zip file.
This triggers an onChange function with a variable of type File (Blob), which includes attributes like:
file name
file size
file type (application/zip)
The javascript code then parses the .zip file, extracts specific data within it and uses it within the web-app.
This works well within the web-app, when the app is called via the Chrome browser.
For example when operated in chrome browser on an Android phone, I can pull the .zip file and open it in the web-app.
I want to do the same but using the mobile app.
I am able to pick up the .zip file using a File Chooser, but I have problems to fetch the file from the Javascript code.
When calling fetch(fileUri) from the Javascript side I'm getting errors.
I'm using the following uri
/storage/emulated/0/Android/data/com.example/files/Download/file2.zip
The fetch succeeds but returns a blob with size of 165 (i.e. not the actual size of the file) which hosts the error message:
{
"error": "Not Found",
"message": "The requested URL was not found on the server. If you entered the URL manually please check your spelling and try again."
}
The program flow is like so:
I select a .zip file via FileChooser.
In onActivityResult, the uri value is /document/msf:12858 (seen via uri = intent.getData();)
The uri needs to be mapped into a real path file url, such that the fileUrl will be passed to Javascript (via webview).
Javascript will then fetch the file using the fileUrl.
I searched how to get the real path file url when selecting a file with FileChooser, and found
this, and this links.
I wasn't able to get the real file path, so I decided to read the file and write it to another location, so I can get a file path. (this is not efficient and done just to check the functionality).
I create the new file using the following code:
InputStream stream = context.getContentResolver().openInputStream(uri);
File file2 = new File(context.getExternalFilesDir(Environment.DIRECTORY_DOWNLOADS), "file2.zip");
writeBytesToFile(stream, file2);
I don't see any errors when creating the file, and when creating the file, the number of bytes that are read and written to the new file are as expected.
For file2, I get a value of:
/storage/emulated/0/Android/data/com.example/files/Download/file2.zip
Then, within the Javascript code I fetch this file path.
But I'm getting a Blob with the "file-not-found" content as above.
So:
How can I verify that the file is indeed created and that the path can be fetched from Javascript?
How can I get the real file path of the original selected file, so I don't have to read and write the original file to new location just to get the file path?
Thanks
EDIT1:
I have "Intent intent" and not "Intent data" in the signature of onActivityResult.
I replaced String filePath = intent.getData() with
protected void onActivityResult(int requestCode, int resultCode, Intent intent) {
super.onActivityResult(requestCode, resultCode, intent);
try {
intent_to_resolve = new JSONObject();
if (resultCode == RESULT_OK) {
// try1
String filePath1 = intent.getData().toString();
Log.d("Verbose", "filePath1: " + filePath1);
// try2
String filePath2 = intent.toString();
Log.d("Verbose", "filePath2: " + filePath2);
...
I'm getting the following value for filePath:
filePath1: content://com.android.providers.downloads.documents/document/msf%3A12858
filePath2: Intent { dat=content://com.android.providers.downloads.documents/document/msf:12858 flg=0x43 }

Trouble loading local html file into default device browser in Android app

I am an iOS developer assigned a task in Android, so bear with me, I'm a bit green in Android.
I am attempting to load a local html file that is stored in the device download directory in a folder called user_guide. I want the html file to load in the device's browser (not in a webview for reasons outside the scope of this post). I am using the following code to launch the browser:
String downloadPath = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS).toString();
String path = "file://" + downloadPath + "/user_guide/index.html"; // + R.raw.test;
Uri pathUrl = Uri.parse(path);
Intent browserIntent = new Intent(Intent.ACTION_VIEW);
browserIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
browserIntent.setData(pathUrl);
context.startActivity(browserIntent);
I obtained the value of path by setting a breakpoint and manually set it in Chrome on my device to verify that is does work and loads the proper file. However, when I try to run this code in the app, I get the following toast message:
Cannot display PDF (index.html is of invalid format)
I'm confused about this message since I am trying to load an html file, not a PDF. Can anyone help me out? THanks!
Try changing "browserIntent.setData(pathUrl)" to
browserIntent.setDataAndType(pathUrl, "text/html")
to explicitly specify that it's HTML.
I found this suggestion at https://stackoverflow.com/a/7009685/10300291.

Image saving do not work if name contain slash

I developing app which send images to server. All image name must begin with scanned code (barcode or QR code) + 5 random numbers.
Everthing works fine if i scan barcode with numbers. But if i scan QR code wich contain slash character / then my app explode.
if I parse scanned QR code and replace / with _ again everything works fine.
This is code where i generate image file
private File createImageFile() throws IOException {
imageName = generateImageName();
File storageDir = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES);
File image = File.createTempFile(imageName, ".png", storageDir);
mCurrentPhotoPath = image.getPath();
mImageNameList.add(imageName);
return image;
}
This is code where i generate image name. Part with replacing characters can be commented.
public String generateImageName() {
int randomNumber = randomGenerator.nextInt((99999 - 100) + 1) + 100;
// Image name generator
if (mCodeContent.contains("http://")) {
mCodeContent = mCodeContent.replace("http://", "");
}
if (mCodeContent.contains("/")) {
mCodeContent = mCodeContent.replace("/", "_");
}
imageName = mCodeContent + "_" + Integer.toString(randomNumber) + ".png";
return imageName;
}
i need full QR code name with slashes
In my opinion it is bad idea to use slashes in filename, because Linux and Android filesystem doesn't allow to use this characters in filename. It may cause serious problems on server side too.
I think that server requirements should be changed in this case.
File name contains slash / is raising exception because this char is reserved for directory, may be replace with Character 'DIVISION SLASH' (U+2215) which looks like ∕, or Character 'FULLWIDTH SOLIDUS' (U+FF0F) which looks like /.
In my opinion you don't actually NEED to name your images with the url of the QR in the first place, that's just the way you designed your solution, but your initial problem probably never involved that by itself.
On top of that you didn't take into account any https:// beginning in your code.
To stay on your request :
Why you can't do it :
"/" is the character to separate folders in the paths of your filesystem, you can't put any in a filename.
What you could do with minimal changes :
encode the url so you don't get "/" but "%2F"

Showing image in WebView from External storage Directory on device

I want to show an image in a webview which has been downloaded externally to ExternalStorageDirectory. I am using the followng code to load the HTML as a string with the base URL set to be that of where the images are saved:
Article article = page.articles.get(0);
String mime = "text/html";
String encoding = "utf-8";
String base = "file:/" + Environment.getExternalStorageDirectory() + "/images_folder/";
Log.v("IMAGE", base);
webView = (WebView)rootView.findViewById(R.id.webView);
webView.setBackgroundColor(Color.TRANSPARENT);
webView.loadDataWithBaseURL(base, article.articleContent, mime, encoding, null);
This code works fine in the emulator but when I try it on a device (Nexus 7 Tablet) the image doesn't load. The image is definitely stored in the External Storage Directory as they can be found using a file explorer on the tablet. I imagine this has something to do with the Nexus 7 using emulated storage but I really don't know, the call Environment.getExternalStorageDirectory() should point to the same directory every time.
The html String being brought in is very simple and looks like this:
<html><head></head><body><img src = 'test_download1.png'></img>This is the first Article for the first page in html</body></html>
Where test_download1.png is a file stored in the External Storage directory.
To access SDCARD in nexus 7 you have to write a different code as your code will give access only to mnt/sdcard and not to actual path,where your image is saved.
code to access SDCARD in nexus 7

image not displaying in flex mobile application using nativePath

I am creating an android application in flash builder 4 using 4.1 SDK on windows. The application first downloads some images from the internet and saves them in the desktopDirectory. Now I want to display downloaded images in my flex mobile application.
Issue:
Images are being downloaded from the internet successfully and saved in the desktopDirectory successfully.
Now when I try to display an image using nativePath then it is not displayed. A small blue icon with a questionmark is displayed instead of the image. The code that I am using is as below:
displayContainer.removeAllElements();
var image:spark.components.Image = new spark.components.Image();
var imageFile:File = File.desktopDirectory.resolvePath(desktopFilePath);
if(imageFile.exists)
{
var imagePath:String = File.desktopDirectory.resolvePath(desktopFilePath).nativePath;
image.source = imagePath;
trace("Image Path: " + imagePath);
displayContainer.addElementAt(image,1);
}
When I trace if the image file exists or not, it shows that the file is there. But the file is not displayed in the app.
However, the image is displayed when I hardcode the image path in the code as below:
<s:Image id="a1" source="data/02.jpg" />
Thus the image is there but the path is not being resolved programmatically.
What am I doing wrong? Please guide.
I am testing my application on an android tablet.
Instead of using file nativePath, I used file url and I got solution to my problem. Please see the code below which is working:
displayContainer.removeAllElements();
var image:spark.components.Image = new spark.components.Image();
var imageFile:File = File.desktopDirectory.resolvePath(desktopFilePath);
if(imageFile.exists)
{
var imagePath:String = File.desktopDirectory.resolvePath(desktopFilePath).url;
image.source = imagePath;
trace("Image Path: " + imagePath);
displayContainer.addElementAt(image,1);
}

Categories

Resources