SDカードでの画像のキャッシュ

最近、 sly2mImageViewから携帯電話のSDカードに画像を保存する方法を説明しました。 誰か(たとえば、個人的に)は、この投稿とは異なるものを期待していました。つまり:



1 インターネットからの画像を操作する

2 。 そのような画像を自動的にダウンロードして保存する

。 高度な画像キャッシュ



興味があるなら、見てください。



したがって、必要な3つのタスクすべてを実行する独自のクラスを作成します。



最初に、クラスフレームワークと、さらに役立ついくつかの追加メソッドを作成します。

package com.habra.imagemanager; public class ImageManager { public String md5(String s) { try { MessageDigest digest = java.security.MessageDigest.getInstance("MD5"); digest.update(s.getBytes()); byte messageDigest[] = digest.digest(); StringBuffer hexString = new StringBuffer(); for (int i = 0; i < messageDigest.length; i++) { hexString.append(Integer.toHexString(0xFF & messageDigest[i])); } return hexString.toString(); } catch (NoSuchAlgorithmException e) { e.printStackTrace(); } return ""; } public static void fileSave(InputStream is, FileOutputStream outputStream) { int i; try { while ((i = is.read()) != -1) { outputStream.write(i); } } catch (IOException e) { e.printStackTrace(); } } }
      
      







md5関数の目的は明確だと思いますが、fileSave関数はInputStreamをFileOutputStreamに保存します。つまり、ネットワークから画像をアップロードしてSDカードに保存します。



次に、ダウンロードしたベクターを作成して、既にダウンロードした写真を保存し、そのようなベクターで作業する方法を作成します。

これは、たとえばListView内のImageView要素に対して複数のロードストリームを一度に実行するなどの不快な影響を排除するために必要です。



 private Vector<ImageView> downloaded = new Vector<ImageView>(); public boolean findObject(ImageView object) { for (int i = 0; i < downloaded.size(); i++) { if (downloaded.elementAt(i).equals(object)) { return true; } } return false; }
      
      







findObjectメソッドは、キューに入っている画像を検索し、見つかった場合はtrueを返します。



そして今、私たちのクラスには2つの主要なメソッドがあります:



 private Bitmap downloadImage(Context context, int cacheTime, String iUrl, ImageView iView) { Bitmap bitmap = null; if (cacheTime != 0) { File file = new File(context.getExternalCacheDir(), md5(iUrl) + ".cache"); long time = new Date().getTime() / 1000; long timeLastModifed = file.lastModified() / 1000; try { if (file.exists()) { if (timeLastModifed + cacheTime < time) { file.delete(); file.createNewFile(); fileSave(new URL(iUrl).openStream(), new FileOutputStream(file)); } } else { file.createNewFile(); fileSave(new URL(iUrl).openStream(), new FileOutputStream( file)); } bitmap = BitmapFactory.decodeStream(new FileInputStream(file)); } catch (Exception e) { e.printStackTrace(); } if (bitmap == null) { file.delete(); } } else { try { bitmap = BitmapFactory.decodeStream(new URL(iUrl).openStream()); } catch (Exception e) { e.printStackTrace(); } } if (iView != null) { downloaded.remove(iView); } return bitmap; } public void fetchImage(final Context context, final int cacheTime, final String url, final ImageView iView) { if (iView != null) { if (findObject(iView)) { return; } downloaded.add(iView); } new AsyncTask<String, Void, Bitmap>() { protected Bitmap doInBackground(String... iUrl) { return downloadImage(context, cacheTime, iUrl[0], iView); } protected void onPostExecute(Bitmap result) { super.onPostExecute(result); if (iView != null) { iView.setImageBitmap(result); } } }.execute(new String[] { url }); }
      
      







したがって、downloadImageメソッド(アクティビティアクティビティ、int cacheTime、String iUrl、ImageView iView)は、Webから画像をダウンロードしてキャッシュします。

そのパラメーター:





しかし、私たちはそれを使用しません(プライベート修飾子に気付きませんでしたか?)、しかし、fetchImage関数はdownloadImageと同じパラメーターを取ります。 fetchImageメソッド自体は、ImageViewのダウンロードリストとイメージのインストールを監視します。

私の謙虚な意見では、コードは直感的であり、コメントを必要としません。 投稿の最後に、クラスの使用例を示します。



 ImageManager man = new ImageManager(); ImageView i1 = (ImageView) findViewById(R.id.i1); ImageView i2 = (ImageView) findViewById(R.id.i2); ImageView i3 = (ImageView) findViewById(R.id.i3); man.fetchImage(this, 3600, "http://habrastorage.org/storage1/51624865/5d7f2b56/333c3c3f/fa5cdc9b.png", i1); man.fetchImage(this, 3600, "http://habrastorage.org/storage1/9042dd3c/acc1f8b3/782ca380/c05ecaf3.png", i2); man.fetchImage(this, 3600, "http://habrastorage.org/storage1/39a0bbce/4f56b8c7/ca84d78f/8b7bf972.png", i3);
      
      







更新: クラスのソースコード

更新2: AsyncTaskを使用してfetchImageメソッドを書き換えました

更新3:アクティビティがコンテキストに変更されました



All Articles