Android菜鸟的提升之路---遇到的有意思的小问题(Animation,沉浸式,glide,AS冷知识,ViewPager)

本文介绍了Android开发中遇到的问题及解决方法,包括使用Glide优化图片加载、处理内存溢出、IntentRun的不同模式、动画设置技巧、沉浸式状态栏实现、ViewPager动态添加视图等。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

最近在写一个项目,就是一个关于儿童的小游戏,不难,但是涉及的图片很多,一开始我在xml文件中直接对ImageView setBackground,结果程序运行着就会崩溃一下,内存溢出比较严重,如何就换了一种方式用Glide去加载,发现好了,但是Glide 有事也会内存溢出,但我目前的项目还没有涉及到,等以后涉及到了再好好研究一下,Glide是个好东西。


注意在定义变量和实例化对象的时候,常常可能出现空指针,要善于利用try catch;


android项目res里面会有一些文件夹


里面放图片(logo)后缀的-hdpi,-mdpi等等代表了所放的图片的大小,同样一张图片放到不同文件夹显示出效果不同,包括drawable文件夹也是一样,一个小东西,具体也不去深究,知道就好,后缀代表dpi大小的一个范围而已。


关于Intent Run:首先它是一个为了编译部署更快而出现的新功能,在Android2.0以后出现的,分三种情况:

hot swap(连activity都不重启) warm swap(仅重启activity)  cool swap(重启app) 除此以外的run就是完全重装apk。


android反编译和代码混淆:反编译可以参考https://blog.youkuaiyun.com/guolin_blog/article/details/49738023;

需要的时候再看一下就ok,代码混淆在AS里面比较简单,在build.gradle里面的minifyEnable true这样设置一下就可以,具体参考https://blog.youkuaiyun.com/guolin_blog/article/details/50451259



写一个app刚刚启动时的广告页面,就是利用了animation动画中的alphaAnimation(透明度动画):

附上代码:

private void setAnimation() {//渐变动画


    AlphaAnimation a = new AlphaAnimation(0.0f, 1);
    a.setDuration(3000);//时间
    a.setAnimationListener(this);//配置监听器
    imageView.startAnimation(a);//启动动画

}

@Override
public void onAnimationStart(Animation animation) {

}//动画开始时的动作

@Override
public void onAnimationEnd(Animation animation) {
    //当动画结束的时候跳转
    startActivity(new Intent(MainActivity.this, shou_ye_activity.class));
    finish();
}//动画结束时的动作

@Override
public void onAnimationRepeat(Animation animation) {

}//动画重复时的动作
这里需要在类前面要加上 
public class MainActivity extends AppCompatActivity implements Animation.AnimationListener
因为要重写动画监听接口中动画结束时的动作。


然后有必要对Animation中的rotateAnimation(旋转)实现一下和对ScaleAnimation(尺寸变化)实现TranslateAnimation(平移变化)

如要对动画设置监听(动画开始,结束,重复)参考上面implement一下接口就可以


这里我都是用xml文件开设置动画的一些属性:

首先在res文件夹下新建一个anim包(里面放动画属性xml文件)

然后就是写动画属性:

第一个是alphaAnimation:

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android" >

    <alpha
        android:duration="5000"//动画时间
        android:fromAlpha="0.5"//开始透明度
        android:toAlpha="1"//结束透明度
android:repeatCount="-1"//重复次数(-1表示无限,可以具体的次数)
android:repeatMode="reverse"(表示回放,开始->结束->开始)可以填restart(表示重头开始  开始->结束)
/></set>

第二个是scaleAnimation:

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android" >

    <scale
        android:duration="5000"//动画时间
        android:fromXScale="1"//开始X尺寸
        android:fromYScale="1"//开始Y尺寸
        android:toXScale="0.5"//结束X尺寸
        android:toYScale="0.5"//结束Y尺寸
        android:pivotX="50%"//变化中心 X
android:repeatCount="-1"//重复次数(-1表示无限,可以具体的次数)
android:repeatMode="reverse"(表示回放,开始->结束->开始)可以填restart(表示重头开始  开始->结束)
android:pivotY="50%" /> //变化中心 Y
</set>

最后就是TranslateAnimation:

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android" >

    <translate
        android:duration="5000" 
        android:fromXDelta="0"//开始时X坐标(可以填数字比如50单位默认px,
                                              可以填50% view的左上角加上view宽度的50%
                                                  可以填50%p view左上角加上父控件宽度的50%)
        android:fromYDelta="0"//开始时Y坐标
        android:toXDelta="100" //结束时X坐标
        android:toYDelta="0"//结束时Y坐标
android:repeatCount="-1"//重复次数(-1表示无限,可以具体的次数)
android:repeatMode="reverse"(表示回放,开始->结束->开始)可以填restart(表示重头开始  开始->结束)

/></set>

属性写完以后就是在调用的问题了。

Animation a = AnimationUtils.loadAnimation(this,R.anim.translate);//选择你要的动画
 imageView.startAnimation(a);
很简单。


沉浸式代码:

先在oncreat中加入:

getWindow().getDecorView().setOnSystemUiVisibilityChangeListener (new View.OnSystemUiVisibilityChangeListener() {
            @Override
            public void onSystemUiVisibilityChange(int visibility) {
                if (visibility == View.SYSTEM_UI_FLAG_VISIBLE) {
                    onWindowFocusChanged(true);
                }
            }
        });


然后写一个方法:

@Override  //沉浸式,去掉状态栏,去掉
    public void onWindowFocusChanged(boolean hasFocus) {
        super.onWindowFocusChanged(hasFocus);
        if (hasFocus && Build.VERSION.SDK_INT >= 19) {
            View decorView = getWindow().getDecorView();
            decorView.setSystemUiVisibility(
                    View.SYSTEM_UI_FLAG_LAYOUT_STABLE
                            | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
                            | View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
                            | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
                            | View.SYSTEM_UI_FLAG_FULLSCREEN
                            | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY);
        }
    }



关于ViewPager动态添加视图的问题,比如我这里添加的是ImageView,首先我添加三张图片:

ImageView imageView = new ImageView(this);
imageView.setImageResource(R.drawable.ka_1);
imageViewList.add(imageView);

imageView.setImageResource(R.drawable.ka_2);
imageViewList.add(imageView);

imageView.setImageResource(R.drawable.ka_3);
imageViewList.add(imageView);

看看逻辑好像没有什么问题,但是最后只会显示一张,再滑一下就报错:

The specified child already has a parent. You must call removeView() on the child's parent first.

意思就是我们首先定义一个imageview,把它背景设置为ka_1,加入到list中,然后我继续设置背景加入到list,这个时候就有问题了,第一次添加了imageview后,那么这个view有它的parent,下次虽然改变了背景但还是添加imageview对象,这是不允许的,因为parent只能有一个,那么改一下代码:

ImageView imageView = new ImageView(this);
imageView.setImageResource(R.drawable.ka_1);
imageViewList.add(imageView);

ImageView imageView1 = new ImageView(this);
imageView1.setImageResource(R.drawable.ka_2);
imageViewList.add(imageView1);

ImageView imageView2 = new ImageView(this);
imageView2.setImageResource(R.drawable.ka_3);
imageViewList.add(imageView2);


new三个对象就可以,当然用for循环把new对象放到循环里面更方便点。




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值