升级targetSdkVersion遇到的问题记录

入职接手的是一个三年多的老项目,targetSdkVersion依然是21(...),2019年部分应用市场对targetSdkVersion做了限制,不得不升级了。

这里记录一些升级到targetSdkVersion=26时遇到的一些问题。

一、升级targetSdkVersion23

  • 无需多说,动态权限申请。
  • scrollView嵌套多个RecyclerView导致RecyclerView显示不全。

    解决方案

  • UI其他的问题,部分View显示不出来,修改xml即可

二、升级targetSdkVersion24


问题1:java.lang.UnsupportedOperationException: TextureView doesn't support displaying a background drawable

源码分析:

TextureView相关源码

@Override
public void setForeground(Drawable foreground) {
    if (foreground != null && !sTextureViewIgnoresDrawableSetters) {
        throw new UnsupportedOperationException(
                "TextureView doesn't support displaying a foreground drawable");
    }
}

@Override
public void setBackgroundDrawable(Drawable background) {
    if (background != null && !sTextureViewIgnoresDrawableSetters) {
        throw new UnsupportedOperationException(
                "TextureView doesn't support displaying a background drawable");
    }
}

View相关源码

/**
    * Allow setForeground/setBackground to be called (and ignored) on a textureview,
    * without throwing
    */
static boolean sTextureViewIgnoresDrawableSetters = false;

// Prior to N, TextureView would silently ignore calls to setBackground/setForeground.
// On N+, we throw, but that breaks compatibility with apps that use these methods.
sTextureViewIgnoresDrawableSetters = targetSdkVersion <= Build.VERSION_CODES.M;



case com.android.internal.R.styleable.View_background:
    background = a.getDrawable(attr);
//这里触发了setBackgroundDrawable
if (background != null) {
    setBackground(background);
}

public void setBackground(Drawable background) {
    //noinspection deprecation
    setBackgroundDrawable(background);
}

可以看出,Viewbackground不为null(不知道原因),且24以后sTextureViewIgnoresDrawableSettersfalse,会在setBackgroundDrawable方法中抛出UnsupportedOperationException异常。

解决方法就是xml中将背景设置为nullbackground不为null的原因还未查明



问题2:android.os.FileUriExposedException file exposed beyond app through Intent.getData()

对于面向 Android 7.0 的应用,Android 框架执行的 StrictMode API 政策禁止在您的应用外部公开 file:// URI。如果一项包含文件 URI 的 intent 离开您的应用,则应用出现故障,并出现 FileUriExposedException 异常。

要在应用间共享文件,您应发送一项 content:// URI,并授予 URI 临时访问权限。进行此授权的最简单方式是使用 FileProvider 类。如需了解有关权限和共享文件的详细信息,请参阅共享文件。

例如安装apk对7.0以上需要做判断,同时需要申明权限



    public static void installApk(final Context context, final File apkFile) {


        Intent intent = new Intent(Intent.ACTION_VIEW);
        Uri data;
        String type = "application/vnd.android.package-archive";
        //7.0以上需要用
        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.N) {
            data = Uri.fromFile(apkFile);
        } else {
            String authority = context.getPackageName() + ".fileprovider";
            data = FileProvider.getUriForFile(context, authority, apkFile);
            intent.setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
        }
        intent.setDataAndType(data, type);
        intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
        try {
            context.startActivity(intent);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }


解决方法:使用FileProvider,可以参考这篇文章

二、升级targetSdkVersion26

Notificaiton通知必须指定Notificaiton Channels

thanks Andriod版本适配 check list

你可能感兴趣的:(升级targetSdkVersion遇到的问题记录)