在学习Android开发的过程中,遇到了一些简单的bug。
本次为了设计一个用户登陆界面,页面确实完成了设计,并且单一使用可以正常显示。
可如果再创建一个页面,并设计一个Button去OnClick它,并用Intent去start新创建的页面,就会出现程序闪退。
再三查找问题,综合网上查询所得,得到解决,但随之的,新的Bug又产生了,新的Bug先不考虑,本文重在解决Intent闪退问题(实际上是Button的findViewById()导致的)。
创建了三个Activity,第一个主启动的MainActivity.class,对应XML为activity_main.xml,第二个为初次学习Android控件布局用的LoginActivity.class,对应activity_login.xml,第三个为LoginActivity_2.class,对应activity_login_2.xml,是对第一个Login的再优化版本。
单刀直入,不摆出无关的代码了。
MainActivity
protected void initView() {
Button loginButton = findViewById(R.id.btn_Login);
loginButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent(MainActivity.this, LoginActivity_2.class);
startActivity(intent);
}
});
}
}
activity_main.xml
<Button
android:id="@+id/btn_Login"
android:layout_width="200dp"
android:layout_height="wrap_content"
android:background="@drawable/bg_login_btn_submit"
android:text="@string/login_btn_text_login"
android:textColor="#FFFFFF"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.497"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintVertical_bias="0.734" />
再看看登陆界面的XML:
activity_login.xml
<Button
android:id="@+id/btn_login"
android:layout_width="0dp"
android:layout_height="55dp"
android:layout_marginStart="16dp"
android:layout_marginTop="8dp"
android:layout_marginEnd="16dp"
android:background="@drawable/bg_login_btn_submit"
android:text="@string/login_btn_text_login"
android:textAlignment="center"
android:textColor="#B3FFFFFF"
android:textStyle="bold"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
报错信息(空指针异常):
Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'void android.widget.Button.setOnClickListener(android.view.View$OnClickListener)' on a null object reference
看到这你是不是很快就明白了错误的原因?没错,就是因为两个XML中的Button的ID相同了,从而导致在MainActivity.class
中使用Button loginButton = findViewById(R.id.btn_Login);
时,系统懵逼了,这是用哪个btn_Login?
至此,本错误就显而易见的可以修改了,只需要将两个xml中的button
的ID
修改为不同值,再在class
里面调用对应的id
即可。
修改activity_main.xml
的Button
的id
为
android:id="@+id/main_btn_Login"
修改activity_login.xml
的Button
的id
为
android:id="@+id/activity1_btn_login"
最后,再在使用Intent
的MainActivity.class
修改id
获取的对象是main_btn_Login
即可。
Button loginButton = findViewById(R.id.main_btn_Login);
另外,再说说在查找问题的过程中发现的其他同类型问题。
id
相同,但xml
居然不报错,太神奇了。Activity
,也就是在AndroidMainifest.xml
里声明,注册如下(非主启动页面):<activity android:name="com.thdmi.login.LoginActivity" />
category
,理论上最新版的Android Studio会自动加上。<category android:name="android.intent.category.LAUNCHER" />
intent
跳转Activity
跳转失败,Activity
生命周期也不执行。分析:应用崩溃后,栈内存在有异常的当前Activity,再次复用时出现了界面闪退问题。解决方案:设置启动模式为singleTask-栈内复用模式
。putExtra
存入key-value
值,在B
中Bundle bun = this.getIntent.getString()
方法会报错。解决方案:从login到welcome报错,去掉B类
的Bundle
就能通过。findViewById()
。private Button loginButton = findViewById(R.id.main_btn_Login);
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
解决方案:findViewById()
不能优先于super.onCreate(savedInstanceState)
和setContentView(R.layout.activity_main)
,修改在之后再进行即可。
综上,好好学习,天天Bug。