FileBackend.java

  1package eu.siacs.conversations.persistance;
  2
  3import java.io.File;
  4import java.io.FileNotFoundException;
  5import java.io.FileOutputStream;
  6import java.io.IOException;
  7import java.io.InputStream;
  8import java.io.OutputStream;
  9import java.lang.ref.WeakReference;
 10
 11import android.content.Context;
 12import android.graphics.Bitmap;
 13import android.graphics.BitmapFactory;
 14import android.net.Uri;
 15import android.util.Log;
 16import android.util.LruCache;
 17import android.view.View;
 18import android.widget.ImageView;
 19import android.widget.TextView;
 20
 21import eu.siacs.conversations.entities.Account;
 22import eu.siacs.conversations.entities.Conversation;
 23import eu.siacs.conversations.entities.Message;
 24import eu.siacs.conversations.services.XmppConnectionService;
 25import eu.siacs.conversations.xmpp.jingle.JingleFile;
 26
 27public class FileBackend {
 28
 29	private static int IMAGE_SIZE = 1920;
 30
 31	private Context context;
 32	private LruCache<String, Bitmap> thumbnailCache;
 33
 34	public FileBackend(Context context) {
 35		this.context = context;
 36		int maxMemory = (int) (Runtime.getRuntime().maxMemory() / 1024);
 37		int cacheSize = maxMemory / 8;
 38		thumbnailCache = new LruCache<String, Bitmap>(cacheSize) {
 39			@Override
 40			protected int sizeOf(String key, Bitmap bitmap) {
 41				return bitmap.getByteCount() / 1024;
 42			}
 43		};
 44
 45	}
 46	
 47	public LruCache<String, Bitmap> getThumbnailCache() {
 48		return thumbnailCache;
 49	}
 50	
 51	public JingleFile getJingleFile(Message message) {
 52		return getJingleFile(message, true);
 53	}
 54
 55	public JingleFile getJingleFile(Message message, boolean decrypted) {
 56		Conversation conversation = message.getConversation();
 57		String prefix = context.getFilesDir().getAbsolutePath();
 58		String path = prefix + "/" + conversation.getAccount().getJid() + "/"
 59				+ conversation.getContactJid();
 60		String filename;
 61		if ((decrypted)||(message.getEncryption() == Message.ENCRYPTION_NONE)) {
 62			filename = message.getUuid() + ".webp";
 63		} else {
 64			filename = message.getUuid() + ".webp.pgp";
 65		}
 66		return new JingleFile(path + "/" + filename);
 67	}
 68
 69	public Bitmap resize(Bitmap originalBitmap, int size) {
 70		int w = originalBitmap.getWidth();
 71		int h = originalBitmap.getHeight();
 72		if (Math.max(w, h) > size) {
 73			int scalledW;
 74			int scalledH;
 75			if (w <= h) {
 76				scalledW = (int) (w / ((double) h / size));
 77				scalledH = size;
 78			} else {
 79				scalledW = size;
 80				scalledH = (int) (h / ((double) w / size));
 81			}
 82			Bitmap scalledBitmap = Bitmap.createScaledBitmap(originalBitmap,
 83					scalledW, scalledH, true);
 84			return scalledBitmap;
 85		} else {
 86			return originalBitmap;
 87		}
 88	}
 89
 90	public JingleFile copyImageToPrivateStorage(Message message, Uri image) {
 91		try {
 92			Log.d("xmppService","copying file: "+image.toString()+ " to internal storage");
 93			InputStream is = context.getContentResolver()
 94					.openInputStream(image);
 95			JingleFile file = getJingleFile(message);
 96			file.getParentFile().mkdirs();
 97			file.createNewFile();
 98			OutputStream os = new FileOutputStream(file);
 99			Bitmap originalBitmap = BitmapFactory.decodeStream(is);
100			is.close();
101			Bitmap scalledBitmap = resize(originalBitmap, IMAGE_SIZE);
102			boolean success = scalledBitmap.compress(
103					Bitmap.CompressFormat.WEBP, 75, os);
104			if (!success) {
105				// Log.d("xmppService", "couldnt compress");
106			}
107			os.flush();
108			os.close();
109			long size = file.getSize();
110			int width = scalledBitmap.getWidth();
111			int height = scalledBitmap.getHeight();
112			message.setBody(""+size+","+width+","+height);
113			return file;
114		} catch (FileNotFoundException e) {
115			// TODO Auto-generated catch block
116			e.printStackTrace();
117		} catch (IOException e) {
118			// TODO Auto-generated catch block
119			e.printStackTrace();
120		}
121
122		return null;
123	}
124
125	public Bitmap getImageFromMessage(Message message) {
126		return BitmapFactory.decodeFile(getJingleFile(message)
127				.getAbsolutePath());
128	}
129
130	public Bitmap getThumbnail(Message message, int size, boolean cacheOnly)
131			throws FileNotFoundException {
132		Bitmap thumbnail = thumbnailCache.get(message.getUuid());
133		if ((thumbnail == null)&&(!cacheOnly)) {
134			Bitmap fullsize = BitmapFactory.decodeFile(getJingleFile(message)
135					.getAbsolutePath());
136			if (fullsize == null) {
137				throw new FileNotFoundException();
138			}
139			thumbnail = resize(fullsize, size);
140			this.thumbnailCache.put(message.getUuid(), thumbnail);
141		}
142		return thumbnail;
143	}
144
145	public void removeFiles(Conversation conversation) {
146		String prefix = context.getFilesDir().getAbsolutePath();
147		String path = prefix + "/" + conversation.getAccount().getJid() + "/"
148				+ conversation.getContactJid();
149		File file = new File(path);
150		try {
151			this.deleteFile(file);
152		} catch (IOException e) {
153			Log.d("xmppService",
154					"error deleting file: " + file.getAbsolutePath());
155		}
156	}
157
158	private void deleteFile(File f) throws IOException {
159		if (f.isDirectory()) {
160			for (File c : f.listFiles())
161				deleteFile(c);
162		}
163		f.delete();
164	}
165}