mirror of https://github.com/M66B/FairEmail.git
Added support for SVG in messages
This commit is contained in:
parent
289d9fc0cd
commit
76ed2d766d
|
@ -79,7 +79,8 @@ public class AdapterImage extends RecyclerView.Adapter<AdapterImage.ViewHolder>
|
||||||
|
|
||||||
private void bindTo(EntityAttachment attachment) {
|
private void bindTo(EntityAttachment attachment) {
|
||||||
if (attachment.available) {
|
if (attachment.available) {
|
||||||
Bitmap bm = ImageHelper.decodeImage(attachment.getFile(context),
|
Bitmap bm = ImageHelper.decodeImage(
|
||||||
|
attachment.getFile(context), attachment.getMimeType(),
|
||||||
context.getResources().getDisplayMetrics().widthPixels);
|
context.getResources().getDisplayMetrics().widthPixels);
|
||||||
if (bm == null)
|
if (bm == null)
|
||||||
ivImage.setImageResource(R.drawable.twotone_broken_image_24);
|
ivImage.setImageResource(R.drawable.twotone_broken_image_24);
|
||||||
|
|
|
@ -726,7 +726,7 @@ public class ContactInfo {
|
||||||
}
|
}
|
||||||
|
|
||||||
@NonNull
|
@NonNull
|
||||||
private static Favicon getFavicon(URL url, String type, int scaleToPixels, Context context) throws IOException {
|
private static Favicon getFavicon(URL url, String mimeType, int scaleToPixels, Context context) throws IOException {
|
||||||
Log.i("GET favicon " + url);
|
Log.i("GET favicon " + url);
|
||||||
|
|
||||||
if (!"https".equals(url.getProtocol()))
|
if (!"https".equals(url.getProtocol()))
|
||||||
|
@ -751,12 +751,7 @@ public class ContactInfo {
|
||||||
if (status != HttpURLConnection.HTTP_OK)
|
if (status != HttpURLConnection.HTTP_OK)
|
||||||
throw new FileNotFoundException("Error " + status + ": " + connection.getResponseMessage());
|
throw new FileNotFoundException("Error " + status + ": " + connection.getResponseMessage());
|
||||||
|
|
||||||
if ("image/svg+xml".equals(type) || url.getPath().endsWith(".svg")) {
|
Bitmap bitmap = ImageHelper.getScaledBitmap(connection.getInputStream(), url.toString(), mimeType, scaleToPixels);
|
||||||
Bitmap bitmap = ImageHelper.renderSvg(connection.getInputStream(), Color.WHITE, scaleToPixels);
|
|
||||||
return new Favicon(bitmap);
|
|
||||||
}
|
|
||||||
|
|
||||||
Bitmap bitmap = ImageHelper.getScaledBitmap(connection.getInputStream(), url.toString(), scaleToPixels);
|
|
||||||
if (bitmap == null)
|
if (bitmap == null)
|
||||||
throw new FileNotFoundException("decodeStream");
|
throw new FileNotFoundException("decodeStream");
|
||||||
else {
|
else {
|
||||||
|
|
|
@ -63,6 +63,7 @@ import java.io.BufferedInputStream;
|
||||||
import java.io.BufferedOutputStream;
|
import java.io.BufferedOutputStream;
|
||||||
import java.io.ByteArrayInputStream;
|
import java.io.ByteArrayInputStream;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
import java.io.FileInputStream;
|
||||||
import java.io.FileNotFoundException;
|
import java.io.FileNotFoundException;
|
||||||
import java.io.FileOutputStream;
|
import java.io.FileOutputStream;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
@ -306,7 +307,10 @@ class ImageHelper {
|
||||||
int scaleToPixels = res.getDisplayMetrics().widthPixels;
|
int scaleToPixels = res.getDisplayMetrics().widthPixels;
|
||||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
|
||||||
try {
|
try {
|
||||||
Drawable d = getScaledDrawable(context, attachment.getFile(context), scaleToPixels);
|
Drawable d = getScaledDrawable(context,
|
||||||
|
attachment.getFile(context),
|
||||||
|
attachment.getMimeType(),
|
||||||
|
scaleToPixels);
|
||||||
if (view != null)
|
if (view != null)
|
||||||
fitDrawable(d, a, scale, view);
|
fitDrawable(d, a, scale, view);
|
||||||
return d;
|
return d;
|
||||||
|
@ -317,7 +321,10 @@ class ImageHelper {
|
||||||
return d;
|
return d;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
Bitmap bm = decodeImage(attachment.getFile(context), scaleToPixels);
|
Bitmap bm = decodeImage(
|
||||||
|
attachment.getFile(context),
|
||||||
|
attachment.getMimeType(),
|
||||||
|
scaleToPixels);
|
||||||
if (bm == null) {
|
if (bm == null) {
|
||||||
Log.i("Image not decodable CID=" + cid);
|
Log.i("Image not decodable CID=" + cid);
|
||||||
Drawable d = context.getDrawable(R.drawable.twotone_broken_image_24);
|
Drawable d = context.getDrawable(R.drawable.twotone_broken_image_24);
|
||||||
|
@ -338,8 +345,9 @@ class ImageHelper {
|
||||||
if (data && (show || inline || a.tracking))
|
if (data && (show || inline || a.tracking))
|
||||||
try {
|
try {
|
||||||
int scaleToPixels = res.getDisplayMetrics().widthPixels;
|
int scaleToPixels = res.getDisplayMetrics().widthPixels;
|
||||||
|
String mimeType = getDataUriType(a.source);
|
||||||
ByteArrayInputStream bis = getDataUriStream(a.source);
|
ByteArrayInputStream bis = getDataUriStream(a.source);
|
||||||
Bitmap bm = getScaledBitmap(bis, "data:" + getDataUriType(a.source), scaleToPixels);
|
Bitmap bm = getScaledBitmap(bis, "data:" + mimeType, mimeType, scaleToPixels);
|
||||||
if (bm == null)
|
if (bm == null)
|
||||||
throw new IllegalArgumentException("decode byte array failed");
|
throw new IllegalArgumentException("decode byte array failed");
|
||||||
|
|
||||||
|
@ -364,7 +372,7 @@ class ImageHelper {
|
||||||
Bitmap bm;
|
Bitmap bm;
|
||||||
int scaleToPixels = res.getDisplayMetrics().widthPixels;
|
int scaleToPixels = res.getDisplayMetrics().widthPixels;
|
||||||
try (InputStream is = context.getContentResolver().openInputStream(uri)) {
|
try (InputStream is = context.getContentResolver().openInputStream(uri)) {
|
||||||
bm = getScaledBitmap(is, a.source, scaleToPixels);
|
bm = getScaledBitmap(is, a.source, null, scaleToPixels);
|
||||||
if (bm == null)
|
if (bm == null)
|
||||||
throw new FileNotFoundException(a.source);
|
throw new FileNotFoundException(a.source);
|
||||||
}
|
}
|
||||||
|
@ -449,7 +457,7 @@ class ImageHelper {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Download image
|
// Download image
|
||||||
Drawable d = downloadImage(context, id, a.source);
|
Drawable d = downloadImage(context, id, a.source, null);
|
||||||
fitDrawable(d, a, scale, view);
|
fitDrawable(d, a, scale, view);
|
||||||
post(d, a.source);
|
post(d, a.source);
|
||||||
} catch (Throwable ex) {
|
} catch (Throwable ex) {
|
||||||
|
@ -599,7 +607,7 @@ class ImageHelper {
|
||||||
|
|
||||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P)
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P)
|
||||||
try {
|
try {
|
||||||
return getScaledDrawable(context, file, dm.widthPixels);
|
return getScaledDrawable(context, file, null, dm.widthPixels);
|
||||||
} catch (IOException ex) {
|
} catch (IOException ex) {
|
||||||
Log.i(ex);
|
Log.i(ex);
|
||||||
return null;
|
return null;
|
||||||
|
@ -617,7 +625,7 @@ class ImageHelper {
|
||||||
}
|
}
|
||||||
|
|
||||||
@NonNull
|
@NonNull
|
||||||
private static Drawable downloadImage(Context context, long id, String source) throws IOException {
|
private static Drawable downloadImage(Context context, long id, String source, String mimeType) throws IOException {
|
||||||
Resources res = context.getResources();
|
Resources res = context.getResources();
|
||||||
DisplayMetrics dm = res.getDisplayMetrics();
|
DisplayMetrics dm = res.getDisplayMetrics();
|
||||||
|
|
||||||
|
@ -677,12 +685,12 @@ class ImageHelper {
|
||||||
try (FileOutputStream fos = new FileOutputStream(file)) {
|
try (FileOutputStream fos = new FileOutputStream(file)) {
|
||||||
Helper.copy(urlConnection.getInputStream(), fos);
|
Helper.copy(urlConnection.getInputStream(), fos);
|
||||||
}
|
}
|
||||||
return getScaledDrawable(context, file, dm.widthPixels);
|
return getScaledDrawable(context, file, null, dm.widthPixels);
|
||||||
}
|
}
|
||||||
|
|
||||||
bm = getScaledBitmap(
|
bm = getScaledBitmap(
|
||||||
urlConnection.getInputStream(),
|
urlConnection.getInputStream(),
|
||||||
source,
|
source, mimeType,
|
||||||
Math.max(dm.widthPixels, dm.heightPixels));
|
Math.max(dm.widthPixels, dm.heightPixels));
|
||||||
} finally {
|
} finally {
|
||||||
if (urlConnection != null)
|
if (urlConnection != null)
|
||||||
|
@ -707,7 +715,7 @@ class ImageHelper {
|
||||||
}
|
}
|
||||||
|
|
||||||
@RequiresApi(api = Build.VERSION_CODES.P)
|
@RequiresApi(api = Build.VERSION_CODES.P)
|
||||||
static Drawable getScaledDrawable(Context context, File file, int scaleToPixels) throws IOException {
|
static Drawable getScaledDrawable(Context context, File file, String mimeType, int scaleToPixels) throws IOException {
|
||||||
Drawable d;
|
Drawable d;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
@ -739,7 +747,7 @@ class ImageHelper {
|
||||||
at android.graphics.ImageDecoder.decodeDrawableImpl(ImageDecoder.java:1758)
|
at android.graphics.ImageDecoder.decodeDrawableImpl(ImageDecoder.java:1758)
|
||||||
at android.graphics.ImageDecoder.decodeDrawable(ImageDecoder.java:1751)
|
at android.graphics.ImageDecoder.decodeDrawable(ImageDecoder.java:1751)
|
||||||
*/
|
*/
|
||||||
Bitmap bm = _decodeImage(file, scaleToPixels);
|
Bitmap bm = _decodeImage(file, mimeType, scaleToPixels);
|
||||||
if (bm == null)
|
if (bm == null)
|
||||||
throw new FileNotFoundException(file.getAbsolutePath());
|
throw new FileNotFoundException(file.getAbsolutePath());
|
||||||
d = new BitmapDrawable(context.getResources(), bm);
|
d = new BitmapDrawable(context.getResources(), bm);
|
||||||
|
@ -749,7 +757,12 @@ class ImageHelper {
|
||||||
return d;
|
return d;
|
||||||
}
|
}
|
||||||
|
|
||||||
static Bitmap getScaledBitmap(InputStream is, String source, int scaleToPixels) throws IOException {
|
static Bitmap getScaledBitmap(InputStream is, String source, String mimeType, int scaleToPixels) throws IOException {
|
||||||
|
if (TextUtils.isEmpty(mimeType))
|
||||||
|
mimeType = Helper.guessMimeType(source);
|
||||||
|
if ("image/svg+xml".equals(mimeType))
|
||||||
|
return ImageHelper.renderSvg(is, Color.WHITE, scaleToPixels);
|
||||||
|
|
||||||
BufferedInputStream bis = new BufferedInputStream(is);
|
BufferedInputStream bis = new BufferedInputStream(is);
|
||||||
|
|
||||||
Log.i("Probe " + source);
|
Log.i("Probe " + source);
|
||||||
|
@ -780,16 +793,23 @@ class ImageHelper {
|
||||||
return new File(dir, id + "_" + Math.abs(source.hashCode()) + extension);
|
return new File(dir, id + "_" + Math.abs(source.hashCode()) + extension);
|
||||||
}
|
}
|
||||||
|
|
||||||
static Bitmap decodeImage(File file, int scaleToPixels) {
|
static Bitmap decodeImage(File file, String mimeType, int scaleToPixels) {
|
||||||
try {
|
try {
|
||||||
return _decodeImage(file, scaleToPixels);
|
return _decodeImage(file, mimeType, scaleToPixels);
|
||||||
} catch (OutOfMemoryError ex) {
|
} catch (IOException | OutOfMemoryError ex) {
|
||||||
Log.e(ex);
|
Log.e(ex);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static Bitmap _decodeImage(File file, int scaleToPixels) {
|
private static Bitmap _decodeImage(File file, String mimeType, int scaleToPixels) throws IOException {
|
||||||
|
if (mimeType == null)
|
||||||
|
mimeType = Helper.guessMimeType(file.getName());
|
||||||
|
if ("image/svg+xml".equals(mimeType))
|
||||||
|
try (FileInputStream fis = new FileInputStream(file)) {
|
||||||
|
return ImageHelper.renderSvg(fis, Color.WHITE, scaleToPixels);
|
||||||
|
}
|
||||||
|
|
||||||
BitmapFactory.Options options = new BitmapFactory.Options();
|
BitmapFactory.Options options = new BitmapFactory.Options();
|
||||||
options.inJustDecodeBounds = true;
|
options.inJustDecodeBounds = true;
|
||||||
BitmapFactory.decodeFile(file.getAbsolutePath(), options);
|
BitmapFactory.decodeFile(file.getAbsolutePath(), options);
|
||||||
|
|
Loading…
Reference in New Issue