【问题标题】:How can I save an image from a url?如何从 url 保存图像?
【发布时间】:2012-04-30 18:28:15
【问题描述】:

我正在使用带有外部图像 URL 的 setImageBitmap 设置 ImageView。我想保存图像,以便以后即使没有互联网连接也可以使用。我可以在哪里以及如何保存它?

【问题讨论】:

    标签: android android-imageview


    【解决方案1】:
    URL imageurl = new URL("http://mysite.com/me.jpg"); 
    Bitmap bitmap = BitmapFactory.decodeStream(imageurl.openConnection().getInputStream()); 
    

    此代码将帮助您从图像 url 生成位图。

    这个question回答了第二部分。

    【讨论】:

      【解决方案2】:

      您必须将其保存在 SD 卡或包数据中,因为在运行时您只能访问这些。这是一个很好的例子

      URL url = new URL ("file://some/path/anImage.png");
      InputStream input = url.openStream();
      try {
      //The sdcard directory e.g. '/sdcard' can be used directly, or 
      //more safely abstracted with getExternalStorageDirectory()
      File storagePath = Environment.getExternalStorageDirectory();
      OutputStream output = new FileOutputStream (storagePath + "/myImage.png");
      try {
          byte[] buffer = new byte[aReasonableSize];
          int bytesRead = 0;
          while ((bytesRead = input.read(buffer, 0, buffer.length)) >= 0) {
              output.write(buffer, 0, bytesRead);
          }
      } finally {
          output.close();
      }
      } finally {
      input.close();
      }
      

      来源:How do I transfer an image from its URL to the SD card?

      【讨论】:

      • 这段代码不会编译。 Environment.getExternalStorageDirectory() 不返回 String
      • 什么是合理尺寸
      • 没错!什么是合理大小?
      • @Denny aReasonableSize 可以是 1024 和 2048。
      • 这是缓冲区大小(也就是一次读/写的字节数)。缓冲区越大,读取/写入的数据块就越多。
      【解决方案3】:

      如果您在应用中使用 KotlinGlide,那么这适合您:

      Glide.with(this)
                      .asBitmap()
                      .load(imageURL)
                      .into(object : SimpleTarget<Bitmap>(1920, 1080) {
                          override fun onResourceReady(bitmap: Bitmap, transition: Transition<in Bitmap>?) {
                              saveImage(bitmap)
                          }
                      })
      

      这就是那个功能

      internal fun saveImage(image: Bitmap) {
          val savedImagePath: String
      
          val imageFileName = System.currentTimeMillis().toString() + ".jpg"
          val storageDir = File(Environment.getExternalStoragePublicDirectory(
                  Environment.DIRECTORY_PICTURES).toString() + "/Folder Name")
          var success = true
          if (!storageDir.exists()) {
              success = storageDir.mkdirs()
          }
          if (success) {
              val imageFile = File(storageDir, imageFileName)
              savedImagePath = imageFile.absolutePath
              try {
                  val fOut = FileOutputStream(imageFile)
                  image.compress(Bitmap.CompressFormat.JPEG, 100, fOut)
                  fOut.close()
              } catch (e: Exception) {
                  e.printStackTrace()
              }
      
              galleryAddPic(savedImagePath)
          }
      }
      
      
      private fun galleryAddPic(imagePath: String) {
          val mediaScanIntent = Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE)
          val f = File(imagePath)
          val contentUri = FileProvider.getUriForFile(applicationContext, packageName, f)
          mediaScanIntent.data = contentUri
          sendBroadcast(mediaScanIntent)
      }
      

      galleryAddPic() 用于查看手机图库中的图片。

      注意:现在如果您遇到文件 uri 异常,那么 this 可以帮助您。

      【讨论】:

        【解决方案4】:

        您可以将图像保存在 sdcard 中,以后无需互联网即可使用该图像。

        see this tutorial 将展示如何存储图像并再次读取它。

        希望这对你有帮助......!

        【讨论】:

          【解决方案5】:

          也许有一天它会帮助像我这样的人

           new SaveImage().execute(mViewPager.getCurrentItem());//calling function
          
          private void saveImage(int currentItem) {
              String stringUrl = Site.BASE_URL + "socialengine/" + allImages.get(currentItem).getMaster();
              Utils.debugger(TAG, stringUrl);
          
              HttpURLConnection urlConnection = null;
              try {
                  URL url = new URL(stringUrl);
                  urlConnection = (HttpURLConnection) url.openConnection();
                  urlConnection.setRequestMethod("GET");
                  urlConnection.setDoOutput(true);
                  urlConnection.connect();
                  File sdCardRoot = Environment.getExternalStorageDirectory().getAbsoluteFile();
          
                  String fileName = stringUrl.substring(stringUrl.lastIndexOf('/') + 1, stringUrl.length());
                  String fileNameWithoutExtn = fileName.substring(0, fileName.lastIndexOf('.'));
          
                  File imgFile = new File(sdCardRoot, "IMG" + System.currentTimeMillis() / 100 + fileName);
                  if (!sdCardRoot.exists()) {
                      imgFile.createNewFile();
                  }
          
                  InputStream inputStream = urlConnection.getInputStream();
                  int totalSize = urlConnection.getContentLength();
                  FileOutputStream outPut = new FileOutputStream(imgFile);
          
                  int downloadedSize = 0;
                  byte[] buffer = new byte[2024];
                  int bufferLength = 0;
                  while ((bufferLength = inputStream.read(buffer)) > 0) {
                      outPut.write(buffer, 0, bufferLength);
                      downloadedSize += bufferLength;
                      Utils.debugger("Progress:", "downloadedSize:" + Math.abs(downloadedSize*100/totalSize));
                  }
                  outPut.close();
                  //if (downloadedSize == totalSize);
                      //Toast.makeText(context, "Downloaded" + imgFile.getPath(), Toast.LENGTH_LONG).show();
              } catch (IOException e) {
                  e.printStackTrace();
              }
          
          }
          
           private class SaveImage extends AsyncTask<Integer, Void, String> {
          
              @Override
              protected String doInBackground(Integer... strings) {
                  saveImage(strings[0]);
                  return "saved";
              }
          
              @Override
              protected void onPostExecute(String s) {
                  Toast.makeText(context, "" + s, Toast.LENGTH_SHORT).show();
              }
          }
          

          【讨论】:

            猜你喜欢
            • 2012-03-30
            • 1970-01-01
            • 1970-01-01
            • 2010-10-17
            • 2015-07-25
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多