AndroidAutoSize使用简介[通俗易懂]

AndroidAutoSize使用简介[通俗易懂]一、简介今日头条屏幕适配方案终极版,一个极低成本的Android屏幕适配方案,项目地址:https://github.com/JessYanCoding/AndroidAutoSize由于此方法是一刀切来适配,所有界面以dp为单位的都会受影响,因此一定要做好防护。二、使用1、集成//集成implementation’me.jessyan:autosize:1.2.1…

大家好,又见面了,我是你们的朋友全栈君。

一、简介

今日头条屏幕适配方案终极版,一个极低成本的 Android 屏幕适配方案,项目地址:https://github.com/JessYanCoding/AndroidAutoSize

由于此方法是一刀切来适配,所有界面以dp为单位的都会受影响,因此一定要做好防护。

二、使用

1、集成

// 集成
implementation 'me.jessyan:autosize:1.2.1'

// 在AndroidManifest中配置
<manifest>
    <application>            
        <meta-data
            android:name="design_width_in_dp"
            android:value="360"/>
        <meta-data
            android:name="design_height_in_dp"
            android:value="640"/>           
     </application>           
</manifest>

在AndroidManifest中配置的是设计图的dp尺寸,比如让UI图给的是1280*720,我们除以2就是640*360,如果UI图是1920*1080,则我们除以3也是640*360, 所以当配置文件里面填写640*360后,1920*1080的图直接除以3设置到界面上即可,1280*720的图除以2设置到界面上即可

2、暂停和停止适配

/**
    需要注意的是暂停AndroidAutoSize后, AndroidAutoSize只是停止了对后续还没有启动的Activity适配的工作,但对已经启动且已经适配的Activity不会有任何影响
/
AutoSizeConfig.getInstance().stop(this);


/**
    需要注意的是重新启动 AndroidAutoSize 后, AndroidAutoSize 只是重新开始了对后续还没有启动的Activity进行适配的工作,但对已经启动且在 stop 期间未适配的Activity不会有任何影响
*/
AutoSizeConfig.getInstance().restart();

3、自定义适配

如果某一UI图的设计分辨率不是1280*720,直接给了一张iPhone的尺寸,那我们就不能按上面的方法进行适配,需要自定义尺寸

public interface CustomAdapt {

    /**
     * 是否按照宽度进行等比例适配 (为了保证在高宽比不同的屏幕上也能正常适配, 所以只能在宽度和高度之中选一个作为基准进行适配)
     *
     * @return {@code true} 为按照宽度适配, {@code false} 为按照高度适配
     */
    boolean isBaseOnWidth();

    /**
     * 返回设计图上的设计尺寸, 单位 dp
     * {@link #getSizeInDp} 须配合 {@link #isBaseOnWidth()} 使用, 规则如下:
     * 如果 {@link #isBaseOnWidth()} 返回 {@code true}, {@link #getSizeInDp} 则应该返回设计图的总宽度
     * 如果 {@link #isBaseOnWidth()} 返回 {@code false}, {@link #getSizeInDp} 则应该返回设计图的总高度
     * 如果您不需要自定义设计图上的设计尺寸, 想继续使用在 AndroidManifest 中填写的设计图尺寸, {@link #getSizeInDp} 则返回 {@code 0}
     *
     * @return 设计图上的设计尺寸, 单位 dp
     */
    float getSizeInDp();
}
public class CustomAdaptActivity extends AppCompatActivity implements CustomAdapt {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_custom_adapt);
    }

    /**
     * 跳转到 {@link FragmentHost}, 展示项目内部的 {@link Fragment} 自定义适配参数的用法
     *
     * @param view {@link View}
     */
    public void goCustomAdaptFragment(View view) {
        startActivity(new Intent(getApplicationContext(), FragmentHost.class));
    }

    /**
     * 是否按照宽度进行等比例适配 (为了保证在高宽比不同的屏幕上也能正常适配, 所以只能在宽度和高度之中选择一个作为基准进行适配)
     *
     * @return {@code true} 为按照宽度进行适配, {@code false} 为按照高度进行适配
     */
    @Override
    public boolean isBaseOnWidth() {
        return false;
    }

    /**
     * 这里使用 iPhone 的设计图, iPhone 的设计图尺寸为 750px * 1334px, 高换算成 dp 为 667 (1334px / 2 = 667dp)
     * <p>
     * 返回设计图上的设计尺寸, 单位 dp
     * {@link #getSizeInDp} 须配合 {@link #isBaseOnWidth()} 使用, 规则如下:
     * 如果 {@link #isBaseOnWidth()} 返回 {@code true}, {@link #getSizeInDp} 则应该返回设计图的总宽度
     * 如果 {@link #isBaseOnWidth()} 返回 {@code false}, {@link #getSizeInDp} 则应该返回设计图的总高度
     * 如果您不需要自定义设计图上的设计尺寸, 想继续使用在 AndroidManifest 中填写的设计图尺寸, {@link #getSizeInDp} 则返回 {@code 0}
     *
     * @return 设计图上的设计尺寸, 单位 dp
     */
    @Override
    public float getSizeInDp() {
        return 667;
    }
}

首先得实现CustomAdapter接口, 同时实现里面isBaseOnWidth()和getSizeInDp()两个方法,前者只能宽高适配二选一,后者是如果基于宽就返回设计图总宽度,如果是基于高,就返回设计图总高度,详见注释。

4、自定义适配Fragment

public class FragmentHost extends AppCompatActivity implements CustomAdapt {
    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_host);
        if (getSupportFragmentManager().findFragmentById(R.id.container1) == null) {
            getSupportFragmentManager().beginTransaction().add(R.id.container1, new CustomFragment1()).commit();
        }
        if (getSupportFragmentManager().findFragmentById(R.id.container2) == null) {
            getSupportFragmentManager().beginTransaction().add(R.id.container2, new CustomFragment2()).commit();
        }
        if (getSupportFragmentManager().findFragmentById(R.id.container3) == null) {
            getSupportFragmentManager().beginTransaction().add(R.id.container3, new CustomFragment3()).commit();
        }
    }

    @Override
    public boolean isBaseOnWidth() {
        return true;
    }

    @Override
    public float getSizeInDp() {
        return 720;
    }
}



public class CustomFragment1 extends Fragment implements CustomAdapt {

    @Nullable
    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
        //由于某些原因, 屏幕旋转后 Fragment 的重建, 会导致框架对 Fragment 的自定义适配参数失去效果
        //所以如果您的 Fragment 允许屏幕旋转, 则请在 onCreateView 手动调用一次 AutoSize.autoConvertDensity()
        //如果您的 Fragment 不允许屏幕旋转, 则可以将下面调用 AutoSize.autoConvertDensity() 的代码删除掉
        AutoSize.autoConvertDensity(getActivity(), 1080, true);
        return createTextView(inflater, "Fragment-1\nView width = 360dp\nTotal width = 1080dp", 0xffff0000);
    }

    @Override
    public boolean isBaseOnWidth() {
        return true;
    }

    @Override
    public float getSizeInDp() {
        return 1080;
    }

    public static View createTextView(LayoutInflater inflater, String content, int backgroundColor) {
        TextView view = new TextView(inflater.getContext());
        ViewGroup.LayoutParams layoutParams =
                new ViewGroup.LayoutParams((AutoSizeUtils.dp2px(inflater.getContext(), 360)),
                        ViewGroup.LayoutParams.MATCH_PARENT);
        view.setLayoutParams(layoutParams);
        view.setText(content);
        view.setTextColor(0xffffffff);
        view.setGravity(Gravity.CENTER);
        view.setTextSize(30);
        view.setBackgroundColor(backgroundColor);
        return view;
    }
}
public class CustomFragment2 extends Fragment implements CustomAdapt{

    @Nullable
    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
        //由于某些原因, 屏幕旋转后 Fragment 的重建, 会导致框架对 Fragment 的自定义适配参数失去效果
        //所以如果您的 Fragment 允许屏幕旋转, 则请在 onCreateView 手动调用一次 AutoSize.autoConvertDensity()
        //如果您的 Fragment 不允许屏幕旋转, 则可以将下面调用 AutoSize.autoConvertDensity() 的代码删除掉
        AutoSize.autoConvertDensity(getActivity(), 720, true);
        return CustomFragment1.createTextView(inflater, "Fragment-2\nView width = 360dp\nTotal width = 720dp", 0xff00ff00);
    }

    @Override
    public boolean isBaseOnWidth() {
        return true;
    }

    @Override
    public float getSizeInDp() {
        return 720;
    }
}
public class CustomFragment3 extends Fragment implements CustomAdapt{

    @Nullable
    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
        //由于某些原因, 屏幕旋转后 Fragment 的重建, 会导致框架对 Fragment 的自定义适配参数失去效果
        //所以如果您的 Fragment 允许屏幕旋转, 则请在 onCreateView 手动调用一次 AutoSize.autoConvertDensity()
        //如果您的 Fragment 不允许屏幕旋转, 则可以将下面调用 AutoSize.autoConvertDensity() 的代码删除掉
        AutoSize.autoConvertDensity(getActivity(), 360, true);
        return CustomFragment1.createTextView(inflater, "Fragment-3\nView width = 360dp\nTotal width = 360dp", 0xff0000ff);
    }

    @Override
    public boolean isBaseOnWidth() {
        return true;
    }

    @Override
    public float getSizeInDp() {
        return 360;
    }
}

5、初始化

public class BaseApplication extends Application {
    @Override
    public void onCreate() {
        super.onCreate();
        //当 App 中出现多进程, 并且您需要适配所有的进程, 就需要在 App 初始化时调用 initCompatMultiProcess()
        //在 Demo 中跳转的三方库中的 DefaultErrorActivity 就是在另外一个进程中, 所以要想适配这个 Activity 就需要调用 initCompatMultiProcess()
        AutoSize.initCompatMultiProcess(this);
        /**
         * 以下是 AndroidAutoSize 可以自定义的参数, {@link AutoSizeConfig} 的每个方法的注释都写的很详细
         * 使用前请一定记得跳进源码,查看方法的注释, 下面的注释只是简单描述!!!
         */
        AutoSizeConfig.getInstance()

                //是否让框架支持自定义 Fragment 的适配参数, 由于这个需求是比较少见的, 所以须要使用者手动开启
                //如果没有这个需求建议不开启,上面3个fragment自定义适配就需要打开这个参数
                .setCustomFragment(true)

                //是否屏蔽系统字体大小对 AndroidAutoSize 的影响, 如果为 true, App 内的字体的大小将不会跟随系统设置中字体大小的改变
                //如果为 false, 则会跟随系统设置中字体大小的改变, 默认为 false
//                .setExcludeFontScale(true)

                //是否打印 AutoSize 的内部日志, 默认为 true, 如果您不想 AutoSize 打印日志, 则请设置为 false
//                .setLog(false)

                //是否使用设备的实际尺寸做适配, 默认为 false, 如果设置为 false, 在以屏幕高度为基准进行适配时
                //AutoSize 会将屏幕总高度减去状态栏高度来做适配
                //设置为 true 则使用设备的实际屏幕高度, 不会减去状态栏高度
//                .setUseDeviceSize(true)

                //是否全局按照宽度进行等比例适配, 默认为 true, 如果设置为 false, AutoSize 会全局按照高度进行适配
//                .setBaseOnWidth(false)

                 //设置屏幕适配逻辑策略类, 一般不用设置, 使用框架默认的就好
//                .setAutoAdaptStrategy(new AutoAdaptStrategy())
        ;
        customAdaptForExternal();
    }

    /**
     * 给外部的三方库 {@link Activity} 自定义适配参数, 因为三方库的 {@link Activity} 并不能通过实现
     * {@link CustomAdapt} 接口的方式来提供自定义适配参数 (因为远程依赖改不了源码)
     * 所以使用 {@link ExternalAdaptManager} 来替代实现接口的方式, 来提供自定义适配参数
     */
    private void customAdaptForExternal() {
        /**
         * {@link ExternalAdaptManager} 是一个管理外部三方库的适配信息和状态的管理类, 详细介绍请看 {@link ExternalAdaptManager} 的类注释
         */
        AutoSizeConfig.getInstance().getExternalAdaptManager()

                //加入的 Activity 将会放弃屏幕适配, 一般用于三方库的 Activity, 详情请看方法注释
                //如果不想放弃三方库页面的适配, 请用 addExternalAdaptInfoOfActivity 方法, 建议对三方库页面进行适配, 让自己的 App 更完美一点
//                .addCancelAdaptOfActivity(DefaultErrorActivity.class)

                //为指定的 Activity 提供自定义适配参数, AndroidAutoSize 将会按照提供的适配参数进行适配, 详情请看方法注释
                //一般用于三方库的 Activity, 因为三方库的设计图尺寸可能和项目自身的设计图尺寸不一致, 所以要想完美适配三方库的页面
                //就需要提供三方库的设计图尺寸, 以及适配的方向 (以宽为基准还是高为基准?)
                //三方库页面的设计图尺寸可能无法获知, 所以如果想让三方库的适配效果达到最好, 只有靠不断的尝试
                //由于 AndroidAutoSize 可以让布局在所有设备上都等比例缩放, 所以只要您在一个设备上测试出了一个最完美的设计图尺寸
                //那这个三方库页面在其他设备上也会呈现出同样的适配效果, 等比例缩放, 所以也就完成了三方库页面的屏幕适配
                //即使在不改三方库源码的情况下也可以完美适配三方库的页面, 这就是 AndroidAutoSize 的优势
                //但前提是三方库页面的布局使用的是 dp 和 sp, 如果布局全部使用的 px, 那 AndroidAutoSize 也将无能为力
                //经过测试 DefaultErrorActivity 的设计图宽度在 380dp - 400dp 显示效果都是比较舒服的
                .addExternalAdaptInfoOfActivity(DefaultErrorActivity.class, new ExternalAdaptInfo(true, 400));
    }
}

customAdapterForExternal()方法里是针对第三方的页面进行适配,一般你是不知道他是基于多少分辨率设计的,因此就需要去尝试,尝试好一个手机后,其余手机应该都没问题了, 如果有多个页面,就不断去add,里面是个map,可以add很多个页面。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/134836.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • rabbitMQ与activeMQ区别

    rabbitMQ与activeMQ区别rabbitMQ 与 activeMQ 区别之前的项目中都用到了这两个消息队列 因此总结一下它们的不同之处 做一个笔记 下次需要的时候再行参考 概念为什么使用消息队列六个字 异步 解耦 削峰 使用了消息队列会有什么缺点一个使用了 MQ 的项目 如果连这个问题都没有考虑过 就把 MQ 引进去了 那就给自己的项目带来了风险 我们引入一个技术 要对这个技术的弊端有充分的认识 才能做好预防 要记住 不要给公司挖坑 从以下两个个角度来考虑 系统可用性降低 你想啊 本来其他系统只要运行好好的 那你的系统就是正常的 现

    2025年7月8日
    1
  • AndroidStudio-断点调试-让你的调试更有效率

    AndroidStudio-断点调试-让你的调试更有效率前言:上篇博客AndroidStudio-断点调试-也许你该知道断点调试是有多么的美好,记录了AndroidStudio上断点调试的基本流程和debug面板按钮介绍.这一篇就给大家分享一点调试的小技巧,让我们的代码调试变得更有效率.你可以选择随时进入调试模式一般我们都是点击绿色小昆虫进入调试模式进行调试,其实还可以有另外一种方法.看下面的面板截图,有没有发现有两个小昆虫图标.图标E

    2022年5月21日
    58
  • VUE组件封装_vue使用组件

    VUE组件封装_vue使用组件什么是组件化:组件化就是将一个页面拆分成一个个小的功能模块,每个功能模块完成属于自己这部分独立的功能,使得整个页面的管理和维护变得非常容易。Vue组件化思想 组件化是Vue中的重要思想,当我们对vue的基本知识有了一定的基础就要开始封装组件了 它提供了一种抽象,让我们可以开发出一个个独立可复用的小组件来构造我们的应用。组件树。组件化思想的应用 1.在项目中充分利用组件化的思想 2.尽可能的将也页面拆分成一个个小的可复用的组件 3.好处:代码更加方便组织和管理,扩展性也更强一.注

    2022年9月23日
    1
  • lnk2019无法解析的外部符号_declspec_无法解析的外部符号lnk2001

    lnk2019无法解析的外部符号_declspec_无法解析的外部符号lnk2001VisualStudio2015编译中出现此问题:errorLNK2019:无法解析的外部符号__vsnprintf,该符号在函数xxxx中被引用解决方案:1、可能是由于某些头文件的函数或者未连接某些链接库所引起,故将头文件和链接库包含进去就OK。2、在项目工程属性中将MFC的使用变为“在共享DLL中使用MFC”3、编译时加入以下代码#include&amp;amp;amp;lt;Windows.h…

    2022年9月25日
    0
  • 算法(一)时间复杂度「建议收藏」

    算法(一)时间复杂度「建议收藏」算法很重要,但是由于做移动开发并不经常用到,所以很多同学早就将算法打了个大礼包送还给了老师了,况且很多同学并没有学习过算法。这个系列就让对算法头疼的同学能快速的掌握基本的算法。过年放假阶段玩了会游戏NBA2K17的生涯模式,没有比赛的日子也都是训练,而且这些训练都是自发的,没有人逼你,从早上练到晚上,属性也不涨,但是如果日积月累,不训练和训练的人的属性值就会产生较大差距。这个突然让我意识到

    2022年5月15日
    39
  • 简单贪吃蛇C++语言编程(如何用c语言写贪吃蛇)

    C语言实现,编译环境VS2017附:easyx图形化(文章末尾)效果图如下(有一些函数kbhit,getch,在这表示为_kbhit与_getch)//不同编译器原因注意在Dev等集成开发软件下可能会CEo(* ̄▽ ̄*)o一、引言作为一个小白,相信大家的心情都是一样的,渴望写一个人生的第一个“贪吃蛇”。…

    2022年4月10日
    425

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号