API 29 已弃用“getBitmap”。还有其他代码吗?

Posted

技术标签:

【中文标题】API 29 已弃用“getBitmap”。还有其他代码吗?【英文标题】:Deprecated "getBitmap" with API 29. Any alternative codes? 【发布时间】:2019-11-01 05:39:32 【问题描述】:

我的onActivityResult 无法正常工作,因为getBitmap 已弃用,是否有任何替代代码可以实现此目的?

这里是需要修改的代码,有什么建议吗?

val bitmap = MediaStore.Images.Media.getBitmap(contentResolver, selectedPhotoUri)

getBitmap 被划掉并表示已弃用

【问题讨论】:

被弃用并不意味着“不起作用”,它意味着该功能将在以后的版本中删除,但仍然可以使用。 【参考方案1】:

这对我有用,

override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) 
        super.onActivityResult(requestCode, resultCode, data)

        if(requestCode == 1 && resultCode == Activity.RESULT_OK && data != null) 

            val selectedPhotoUri = data.data
            try 
                selectedPhotoUri?.let 
                    if(Build.VERSION.SDK_INT < 28) 
                        val bitmap = MediaStore.Images.Media.getBitmap(
                            this.contentResolver,
                            selectedPhotoUri
                        )
                        imageView.setImageBitmap(bitmap)
                     else 
                        val source = ImageDecoder.createSource(this.contentResolver, selectedPhotoUri)
                        val bitmap = ImageDecoder.decodeBitmap(source)
                        imageView.setImageBitmap(bitmap)
                    
                
             catch (e: Exception) 
                e.printStackTrace()
            
        
    

【讨论】:

它给我的结果是意外错误不支持位图配置:“硬件” MediaStore.Images.Media.getBitmap( contentResolver,uri) 也被贬低了。 :( Rishav Singla,使用这行代码。 imageBitmap = imageBitmap.copy(Bitmap.Config.ARGB_8888, true); 此方法在 API 级别 29 official doc 中已弃用。为什么你使用if(Build.VERSION.SDK_INT &lt; 28) 它需要 API 级别 28,对于较低的 API 使用旧方式【参考方案2】:

这对我在 java 中很有效

ImageDecoder.Source source = ImageDecoder.createSource(this.getContentResolver(), pictureUri);
Bitmap bitmap = ImageDecoder.decodeBitmap(source);

【讨论】:

它需要 API 级别 28,那么旧的 API 级别呢? 如果 (Build.VERSION.SDK_INT >= 29) val source = ImageDecoder.createSource(it.contentResolver, documentUri) ImageDecoder.decodeBitmap(source) else MediaStore. Images.Media.getBitmap(it.contentResolver, documentUri) 【参考方案3】:

你可以使用:

    private fun getCapturedImage(selectedPhotoUri: Uri): Bitmap 
        val bitmap = when 
            Build.VERSION.SDK_INT < 28 -> MediaStore.Images.Media.getBitmap(
                this.contentResolver,
                selectedPhotoUri
            )
            else -> 
                val source = ImageDecoder.createSource(this.contentResolver, selectedPhotoUri)
                ImageDecoder.decodeBitmap(source)
            
        

【讨论】:

【参考方案4】:

查看official doc:

此方法在 API 级别 29 中已弃用。 图像的加载应通过ImageDecoder#createSource(ContentResolver, Uri) 执行,它提供了 PostProcessor 等现代功能。

【讨论】:

谢谢!关于如何将其用于现有代码的任何建议? @jaedstermedina 该方法已弃用,未删除。另一种方法是答案中报告的方法。与gradle版本或android插件无关,与采用api 29有关。【参考方案5】:

您可以使用此代码创建位图

Bitmap bitmap;
if (Build.VERSION.SDK_INT >= 29) 
     ImageDecoder.Source source = ImageDecoder.createSource(getApplicationContext().getContentResolver(), imageUri);
     try 
         bitmap = ImageDecoder.decodeBitmap(source);
      catch (IOException e) 
         e.printStackTrace();
     
 else 
     try 
     bitmap = MediaStore.Images.Media.getBitmap(getApplicationContext().getContentResolver(), imageUri);
      catch (IOException e) 
          e.printStackTrace();
     

【讨论】:

应该是&gt;= 28 28 和 29 都应该没问题,因为旧的在 29 中已弃用,而新的在 28 中出现。【参考方案6】:

我创建了一个用于从 uri 加载位图的类:

public class BitmapResolver 
    private final static String TAG = "BitmapResolver";

    @SuppressWarnings("deprecation")
    private static Bitmap getBitmapLegacy(@NonNull ContentResolver contentResolver, @NonNull Uri fileUri)
        Bitmap bitmap = null;

        try 
            bitmap = MediaStore.Images.Media.getBitmap(contentResolver, fileUri);
         catch (IOException e) 
            e.printStackTrace();
        

        return bitmap;
    

    @TargetApi(Build.VERSION_CODES.P)
    private static Bitmap getBitmapImageDecoder(@NonNull ContentResolver contentResolver, @NonNull Uri fileUri)
        Bitmap bitmap = null;

        try 
            bitmap = ImageDecoder.decodeBitmap(ImageDecoder.createSource(contentResolver, fileUri));
         catch (IOException e) 
            e.printStackTrace();
        

        return bitmap;
    

    public static Bitmap getBitmap(@NonNull ContentResolver contentResolver, Uri fileUri)
        if (fileUri == null)
            Log.i(TAG, "returning null because URI was null");
            return null;
        

        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P)
            return getBitmapImageDecoder(contentResolver, fileUri);
         else
            return getBitmapLegacy(contentResolver, fileUri);
        
    
   

只是为了节省你一些时间......

【讨论】:

很好,现在在 kotlin 上 仍然无法在此代码中工作。我认为 decodeBitmap 方法需要在工作线程中运行。有什么解决办法吗?【参考方案7】:

很明显,getBitmap API 不适用于最新的 Android SDK - 29。所以,这对我有用

Uri contentURI = data.getData();
try 
    imageView.setImageURI(contentURI);
 catch (Exception e) 
    e.printStackTrace();

如果这对你们中的任何人都不起作用,请告诉我,是否还有其他选择!

【讨论】:

【参考方案8】:

ImageDecoder.createSource(this.getContentResolver(), pictureUri)

工作正常,但要能够使用此代码,mindSdkVersion 至少应为 28。

【讨论】:

【参考方案9】:

你试过了吗?

val bitmap = ImageDecoder.createSource(contentResolver, uri)

【讨论】:

它需要 AP 28【参考方案10】:

你好,你检查 api 设备

var Image_select: String? = null
var bitmap:Bitmap?=null

you show image set

binding?.ImAvator?.setImageURI(data!!.data)


 try 
                    val uri: Uri? = data!!.data
                    bitmap = if(Build.VERSION.SDK_INT>=29)
                        val source: ImageDecoder.Source = ImageDecoder.createSource(requireActivity()
                            .contentResolver, uri!!)
                        ImageDecoder.decodeBitmap(source)
                     else
                        MediaStore.Images.Media.getBitmap(requireActivity().contentResolver, uri!!)
                    
               

                 catch (e: IOException) 
                    e.printStackTrace()
                

上传图片时

压缩位图发送服务器

 fun Camparse() 
        val size = (bitmap!!.height * (812.0 / bitmap!!.width)).toInt()
        val b = Bitmap.createScaledBitmap(bitmap!!, 812, size, true)
        val by = ByteArrayOutputStream()
        b.compress(Bitmap.CompressFormat.JPEG, 100, by)
        val bytes = by.toByteArray()
        Image_select = Base64.encodeToString(bytes, 0)
    

【讨论】:

【参考方案11】:

对于 API 级别 29 中已弃用的 MediaStore.Images.Media.getBitmap(),您可以使用以下代码:

@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) 
    super.onActivityResult(requestCode, resultCode, data);
    if(resultCode == Activity.RESULT_OK) 
        if (requestCode == GALLERY_REQUEST) 
            Uri selectedImage = data.getData();
            try 
                if (Build.VERSION.SDK_INT < 29) 
                    Bitmap bitmap = MediaStore.Images.Media.getBitmap(getActivity().getContentResolver(), selectedImage);
                    imageView2.setImageBitmap(bitmap);
                 else 
                    ImageDecoder.Source source = ImageDecoder.createSource(getActivity().getContentResolver(), selectedImage);
                    Bitmap bitmap = ImageDecoder.decodeBitmap(source);
                    imageView2.setImageBitmap(bitmap);
                
             catch (IOException e) 
                Toast.makeText(getContext(), R.string.error_read_image, Toast.LENGTH_LONG).show();
            
        
    

问候。

【讨论】:

【参考方案12】:

尝试使用 ImageDecoder

bitmap = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) 
    val src:ImageDecoder.Source = ImageDecoder.createSource(contentResolver, selectedPhotoUri!!)
    ImageDecoder.decodeBitmap(src)

else
    @Suppress("DEPRECATION")
    MediaStore.Images.Media.getBitmap(contentResolver, selectedPhotoUri)

【讨论】:

【参考方案13】:
if(result.resultCode == Activity.RESULT_OK && result.data != null 
binding?.ivImage?.setImageURI(result.data?.data)

【讨论】:

【参考方案14】:

此代码适用于我的情况:

override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) 
    super.onActivityResult(requestCode, resultCode, data)
    try 
            when (requestCode) 

                //get the image with camera
                SECTIONCAMERA -> 
                    val imageBitmap = data?.extras?.get("data") as Bitmap
                  ImageView_imagePerfil.setImageBitmap(imageBitmap)

                
                //get the image in gallery
                SECTIONGALLERY -> 
                    val imageUri = data?.data
                    ImageView_imagePerfil.setImageURI(imageUri) 
            

     catch (e: Exception)
             e.printStackTrace()
    

【讨论】:

以上是关于API 29 已弃用“getBitmap”。还有其他代码吗?的主要内容,如果未能解决你的问题,请参考以下文章

ConnectivityManager.getActiveNetworkInfo() / NetworkInfo 在 API 29 中已弃用。有啥替代方案?

我需要创建 Android 键盘应用程序,但有些类已弃用

PayPal REST SDK 已弃用

获取错误java在flutter中使用或覆盖带有contacts_service包的已弃用API

UIApplicationDidChangeStatusBarOrientationNotification 已弃用,还有其他选择吗?

如何在 RAML 中将 REST 服务标记为已弃用