How to compress Ti.utils.base64encode and decompress using .Net method? - android

Does anyone know how to compress Ti.Utils.base64encode??
for example i have this code :
uploadFile = Ti.Filesystem.getFile(pathFile, listing[_fileCtr].toString());
uploadFileName = listing[_fileCtr].toString();
encodedFile = Ti.Utils.base64encode(uploadFile.read()).toString();
//Send Image to .NET web service
And this is the method in my web services for decompressing image from titanium (if i can compress my image before):
static byte[] Decompress(byte[] input)
{
using (MemoryStream output = new MemoryStream(input))
{
using (GZipStream zip = new GZipStream(output, CompressionMode.Decompress))
{
List<byte> bytes = new List<byte>();
int b = zip.ReadByte();
while (b != -1)
{
bytes.Add((byte)b);
b = zip.ReadByte();
}
return bytes.ToArray();
}
}
Until now, i can't find some method for compressing my byte array so i can decompress them using my .NET method..
If u guys have any information about my problem, please tell me..
Many thanks.. :)

In .Net you can use System.Convert.FromBase64String to converts the specified string, which encodes binary data as base-64 digits, to an equivalent 8-bit unsigned integer array.
System.Convert.FromBase64String(encodedString);

Related

To how convert protobuf object to ByteArray and the encode with Base64 URL_SAFE in Swift?

In Android, I could convert an object to ByteArray and then encode it to Base64 (URL_SAFE) as per code below
val myByteArrayObject = protobufObject.toByteArray()
val meEncodedObject = android.util.Base64.encodeToString.encodeToString(
myByteArrayObject, android.util.Base64.DEFAULT).trim()
How could I achieve that in Swift?
Found the answer.
do {
let protobufSerialized = try protobufObject.serializedData()
let protobufEncoded = protobufSerialized.base64EncodedString()
// Do whatever need to be done with the protobufEncoded
} catch { }
The main hidden function that is hard to find is serializedData() that exist on SwiftProtobuf.Message

Rendering jp2(jpeg2000) to Imageview in android.

I am getting jp2 in base64 format from server end. I am able to convert jpg to jp2 form ImageMagick library and send to server. They are able to convert it to jpg using Buffered Image and ImageIo .
But I am not getting any idea to convert jp2 to jpg and render in Imageview.
Hoping for any help. Thanks in advance.
You probably solved it somehow already, but in case you're still looking for a solution, you can try the JP2 for Android library. (Disclaimer: I wrote the library.) It's based on OpenJPEG, like the DimaArts' response, but it has a bit nicer Java interface.
Add the following dependency to your build.gradle file:
implementation 'com.gemalto.jp2:jp2-android:1.0'
and use the following code to decode the JP2:
byte[] jp2Data = ...; //get the JP2 data from somewhere
Bitmap bmp = new JP2Decoder(jp2Data).decode();
imgView.setImageBitmap(bmp);
You can use OpenJpeg library for decode Jpeg2000. You can use compiled library https://github.com/DimaArts/OpenJpegAndroid. It contains an example of encode jpeg2000. Library supports PNG input and output formats for decoder and encoder.
Try this:
OpenJPEGJavaDecoder decoder = new OpenJPEGJavaDecoder();
String[] params2 = new String[4];
params2[0] = "-i";
params2[1] = mInputPath; // path to jp2
params2[2] = "-o";
params2[3] = mOutputPath // path to png
decoder.decodeJ2KtoImage(params2);
if you are using JNI:
public int decodeJ2KtoImage(String[] parameters) {
return internalDecodeJ2KtoImage(parameters);
}
Try this code from https://stackoverflow.com/a/39103107/2760681
private static void convertImage(int randNum) throws IOException {
try {
File foundFile = new File("c:\\images\\" + randNum + ".jp2");
BufferedImage background = ImageIO.read(foundFile);
ImageIO.write(background, "jpg", new File("c:\\images\\" + randNum + ".jpg"));
System.out.println("jpg file is generated");
} catch (Exception e) {
// TODO: handle exception
System.out.println("No file " + randNum +".jp2 found");
}
}

Load image from binary base64

EDIT: This is a bug in Android version <4.3 Kitkat. It relates to the libjpeg library in Android, which can't handle JPEGs with missing EOF/EOI bits, or apparently with metadata/EXIF data that it doesn't like.
https://code.google.com/p/android/issues/detail?id=9064
ORIGINAL QUESTION:
I have an issue when loading an image in my app.
My endpoint sends JSON which contains a BASE64 encoded image. Depending on the REST call, these images can be PNG or JPG. Some of the JPG files suffer from an issue where they are missing an EOF bit at the end. The PNG files work, and some JPG files work, but unfortunately a lot of these JPG files with the issue are present in the Oracle DB (stored as BLOB). I don't have control of the DB.
I have been looking through Google bugs here:
https://code.google.com/p/android/issues/detail?id=9064
and here:
https://code.google.com/p/android/issues/detail?id=57502
The issue is also seen where the encoding is CYMK using a custom ICC profile.
Decoding the image the standard way returns false:
byte[] imageAsBytes = Base64.decode(base64ImageString, Base64.DEFAULT);
return BitmapFactory.decodeByteArray(imageAsBytes, 0, imageAsBytes.length);
According to the bug reports above, the built in JPG parser in Android is to blame.
I'm trying to figure out a workaround for my device, which is stuck on 4.2.2. I have no other option on this OS version.
I thought it might be a good idea to try and use an image loader library like Universal Image Loader, but it requires I either have the image stored locally, or stored on a URL. As I get the data in BASE64 from the REST server, I can't use this. An option is to support decodeByteArray in a custom class that extends BaseImageDecoder, as stated by the dev at the bottom here: https://github.com/nostra13/Android-Universal-Image-Loader/issues/209
Here's where I get stuck. I already have a custom image decoder to try handle the issue of the missing EOF marker in the JPG file, but I don't know how to edit it to add support for decodeByteArray.
Here is my CustomImageDecoder:
public class CustomImageDecoder extends BaseImageDecoder {
public CustomImageDecoder(boolean loggingEnabled) {
super(loggingEnabled);
}
#Override
protected InputStream getImageStream(ImageDecodingInfo decodingInfo) throws IOException {
InputStream stream = decodingInfo.getDownloader()
.getStream(decodingInfo.getImageUri(), decodingInfo.getExtraForDownloader());
return stream == null ? null : new JpegClosedInputStream(stream);
}
private class JpegClosedInputStream extends InputStream {
private static final int JPEG_EOI_1 = 0xFF;
private static final int JPEG_EOI_2 = 0xD9;
private final InputStream inputStream;
private int bytesPastEnd;
private JpegClosedInputStream(final InputStream iInputStream) {
inputStream = iInputStream;
bytesPastEnd = 0;
}
#Override
public int read() throws IOException {
int buffer = inputStream.read();
if (buffer == -1) {
if (bytesPastEnd > 0) {
buffer = JPEG_EOI_2;
} else {
++bytesPastEnd;
buffer = JPEG_EOI_1;
}
}
return buffer;
}
}
}
By the way, using the above custom class, I am trying to load my byte array like this:
byte[] bytes = Base64.decode(formattedB64String, Base64.NO_WRAP);
ByteArrayInputStream is = new ByteArrayInputStream(bytes);
String imageId = "stream://" + is.hashCode();
...
ImageLoader imageLoader = ImageLoader.getInstance();
imageLoader.displayImage(imageId, userImage, options);
and I get this error:
ImageLoader: Image can't be decoded [stream://1097215584_656x383]
Universal Image loader does not allow the stream:// schema, so I created a custom BaseImageDownloader class that allows it:
public class StreamImageDownloader extends BaseImageDownloader {
private static final String SCHEME_STREAM = "stream";
private static final String STREAM_URI_PREFIX = SCHEME_STREAM + "://";
public StreamImageDownloader(Context context) {
super(context);
}
#Override
protected InputStream getStreamFromOtherSource(String imageUri, Object extra) throws IOException {
if (imageUri.startsWith(STREAM_URI_PREFIX)) {
return (InputStream) extra;
} else {
return super.getStreamFromOtherSource(imageUri, extra);
}
}
}
So if anyone can help me create a better CustomImageDecoder that handles a BASE64 encoded string, or a byte[] containing an image so I can use decodeByteArray, I would be grateful!
Thank you.
UnversalImageLoader uses the following schemes to decode the files
"h t t p ://site.com/image.png" // from Web
"file:///mnt/sdcard/image.png" // from SD card
"file:///mnt/sdcard/video.mp4" // from SD card (video thumbnail)
"content://media/external/images/media/13" // from content provider
"content://media/external/video/media/13" // from content provider (video thumbnail)
"assets://image.png" // from assets
"drawable://" + R.drawable.img // from drawables (non-9patch images)
your scheme is stream://
Hope that helps.
Just to close this off:
The issue here is actually a bug in Android <4.3 where Android can't display images that either aren't closed properly (missing end bytes) or contain certain metadata that, for some reason, it doesn't like. I'm not sure what metadata this is, however. My issue was with JPEGs not being terminated properly.
The bug is fixed in Android 4.3 anyway.

Microsoft Face API for Android

I am going through the Get Started tutorial for Microsoft's Face API for Android handhelds. As of right now, everything except for the recognition part works. I can browse through photos alright. However, the detect method somehow always returns null and so no red rectangle is drawn. If someone has already successfully gone through the tutorial, I would be grateful if you could help me. Here is the detect method:
public Face[] detect(InputStream image, boolean analyzesFaceLandmarks, boolean analyzesAge, boolean analyzesGender, boolean analyzesHeadPose) throws ClientException, IOException {
Map<String, Object> params = new HashMap<>();
params.put("analyzesAge", analyzesAge);
params.put("analyzesGender", analyzesGender);
params.put("analyzesFaceLandmarks", analyzesFaceLandmarks);
params.put("analyzesHeadPose", analyzesHeadPose);
String path = ServiceHost + "/detections";
String uri = WebServiceRequest.getUrl(path, params);
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
int bytesRead;
byte[] bytes = new byte[1024];
while ((bytesRead = image.read(bytes)) > 0) {
byteArrayOutputStream.write(bytes, 0, bytesRead);
}
byte[] data = byteArrayOutputStream.toByteArray();
params.clear();
params.put("data", data);
String json = this.restCall.request(uri, "POST", params, "application/octet-stream");
Type listType = new TypeToken<List<Face>>() {
}.getType();
List<Face> faces = this.gson.fromJson(json, listType);
return faces.toArray(new Face[faces.size()]);
}
It looks as if the code you have posted is fine. This makes me wonder if the issue might be with the InputStream you are passing in as the input parameter. It might be that having read the source into the InputStream the position of the stream is at the end and therefore when you read from it nothing is being uploaded to the api.
I was suggesting you check the amount of image data you are uploading:
byte[] data = byteArrayOutputStream.toByteArray();
int length = data.length; // <- what is this value?
It might be necessary to reset the stream position to the beginning before reading it again. Something like this may be required before reading from image
if(image.markSupported())
{
image.reset();
}
BTW, my java is very rusty so there might be better code to use but hopefully you get the gist.

Sending an image as a Base64.encodeToString from android to c# how to get that image

From my android app I am sending an image to C# server converting it to Base64
#Override
public void onPictureTaken(byte[] data, Camera camera)
{
String image = Base64.encodeToString(data, Base64.DEFAULT);
sendtoserver(image);
}
from the server side I received a string but don't know how to convert it and save it.For help I am getting this string tell me how to convert it and save it in C#
/9j/4AAQSkZJRgABAQAAAQABAAD/2wBDAAEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQH/2wBDAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQ
Did you try using Convert.FromBase64String(string s) ?
Source: http://msdn.microsoft.com/en-us/library/system.convert.frombase64string.aspx
UPDATE (posted here instead of in the comments, since the code would display better)
Your Base64 representation is incorrect. For the image you gave in the comments, the Base64 representation is 339801 characters long.
I used the following code to generate a Base64 representation:
string path = #"C:\1XlqZF2.jpg";
Image img = Image.FromFile(path);
byte[] arr;
using (MemoryStream ms = new MemoryStream())
{
img.Save(ms, ImageFormat.Jpeg);
arr = ms.ToArray();
}
String b64 = Convert.ToBase64String(arr);
What is the Base64 class you are using ? I couldn't find it on MSDN.

Categories

Resources