<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<Button
android:id="@+id/Button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:text="Button"/>
LinearLayout>
public class LeftFragment extends Fragment {
LeftFragmentBinding binding;
@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
/**
* 普通写法:
* View view = inflater.inflate(R.layout.left_fragment,container,false);
* retuen view;
* 不需要重写onDestroyView
*/
binding = LeftFragmentBinding.inflate(inflater,container,false);
return binding.getRoot();
}
public void f(){
Log.d("F","SSS");
}
@Override
public void onDestroyView() {
super.onDestroyView();
binding = null;
}
}
重写onCreateView方法。
因为要保持binding的生命周期在有效范围内,所以需要在onDestroy
中让binding=null
。
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<fragment
android:id="@+id/Leftfragment"
android:name="com.example.fragment.LeftFragment"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"/>
LinearLayout>
使用android:name
指定加载的类,注意需要有完整的包名。
新建一个用于替换的布局文件,another_left_fragment.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:background="#ffff00"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:textSize="24sp"
android:text="This is Fragment"/>
LinearLayout>
public class AnotherRightFragment extends Fragment {
@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
return inflater.inflate(R.layout.another_right_fragment,container,false);
}
}
public class MainActivity extends AppCompatActivity implements View.OnClickListener{
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//获取FragmentManager实例,通过向下转型为LeftFragment
LeftFragment leftFragment = (LeftFragment) getSupportFragmentManager().findFragmentById(R.id.Leftfragment);
//调用button按钮的监听器
leftFragment.binding.Button.setOnClickListener(this);
}
@Override
public void onClick(View view) {
int Id = view.getId();
if(Id == R.id.Button){
/**
* 匿名替换的方式:
* getSupportFragmentManager().beginTransaction().replace(R.id.Leftfragment,new AnotherRightFragment()).commit();
*/
replaceFragment(new AnotherRightFragment());
}
}
private void replaceFragment(Fragment fragment){
//1、获取FragmentManager实例
FragmentManager fragmentManager = getSupportFragmentManager();
//2、开启一个事物
FragmentTransaction transaction = fragmentManager.beginTransaction();
//3、向指定名称Id的容器内替换碎片实例
transaction.replace(R.id.Leftfragment,fragment);
//4、提交事物
transaction.commit();
}
}
我们成功实现了向活动中动态添加碎片的功能,不过尝试一下就会发现,通过点击按钮添加了一个碎片之后,这时按下Back键程序就会直接退出。如果这里我们想模仿类似于返回栈的效果,按下Bck键可以回到上一个碎片,该如何实现呢?其实很简单FragmentTransaction
中提供了一个addToBackStack()
方法,可以用于将一个事务添加到返回栈中,修改MainActivity
中的代码,如下所示:
private void replaceFragment(Fragment fragment){
//获取FragmentManager实例
FragmentManager fragmentManager = getSupportFragmentManager();
//开启一个事物
FragmentTransaction transaction = fragmentManager.beginTransaction();
//向指定名称Id的容器内替换碎片实例
transaction.replace(R.id.Rightfragment,fragment);
//添加返回栈
transaction.addToBackStack(null);
//提交事物
transaction.commit();
}
其实我们已经用过很多次了,就是先获取LeftFragment
的实例,如何通过实例中的binding
访问Button
的行为,这就是获取一个碎片,如何调用碎片中的方法。
//获取FragmentManager实例,通过向下转型为LeftFragment
LeftFragment leftFragment = (LeftFragment) getSupportFragmentManager().findFragmentById(R.id.Leftfragment);
使用getActivit
即可,因为获得的活动本身就是一个Context
对象
MainActivit activit = (MainActivit) getActivit();
状态:
FragmentTransaction
的remove()
、replace()
方法将碎片从活动中移除,但如果在事务提交之前调用addToBackStack()
方法,这时的碎片也会进入到停止状态。回调方法:
一般**onCreateView()**用于初始化Fragment的视图,**onViewCreated()一般用于初始化视图内各个控件,而onCreate()**用于初始化与Fragment视图无关的变量。
另外值得一提的是,在碎片中你也是可以通过onSaveInstanceState()
方法来保存数据的,因为进入停止状态的碎片有可能在系统内存不足的时候被回收。保存下来的数据在onCreate()
、onCreateview()
和onActivityCreated()
这3个方法中你都可以重新得到,它们都含有一个Bundle
类型的savedInstanceState
参数。
Android Studio中res下创建layout-large
版本:Android Studio Flamingo | 2022.2.1 Patch 2
在res右键Android resource file,resource type选择layout,available qualifiers选择Size,在右侧chosen qualifiers选择large,最后输入file name,新建成功,这样在res目录下自动新建layout-large文件夹,并在文件夹中生成刚输入的file name的布局文件
常见限定符参考表:
最小宽度限定符允许我们对屏幕的宽度指定一个最小值(以中为单位),然后以这个最小值为临界点,屏幕宽度大于这个值的设备就加载一个布局,屏幕宽度小于这个值的设备就加载另一个布局。
这就意味着,当程序运行在屏幕宽度大于600dp的设备上时,会加载layout–sw600 dp/activity main布局,当程序运行在屏幕宽度小于600dp的设备上时,则仍然加载默认的layout/activity main布局。